Juliaの関数の完全なLLVM IRの出力方法
追記(2018/9/7): 配列を含むコードをコンパイルしたい旨を追加
以下のようにJuliaの組み込み型を用いる関数をLLVM IRを経由してPTXにコンパイルしようと試みています。
Juliaにはcode_llvm関数があるので、これによってJuliaで定義された関数をLLVM IRにコンパイルしてみました:
using InteractiveUtils
function main()
a = [1.0, 2.0]
b = [3.0, 4.0]
a + b
end
code_llvm(main, ())
このcode_llvmによって以下が出力されました。
define nonnull %jl_value_t addrspace(10)* @japi1_main_36013(%jl_value_t addrspace(10)*, %jl_value_t addrspace(10)**, i32) #0 {
L20:
%3 = alloca %jl_value_t addrspace(10)*, i32 3
%gcframe = alloca %jl_value_t addrspace(10)*, i32 4
%4 = bitcast %jl_value_t addrspace(10)** %gcframe to i8*
call void @llvm.memset.p0i8.i32(i8* %4, i8 0, i32 32, i32 0, i1 false)
%5 = alloca %jl_value_t addrspace(10)**, align 8
store volatile %jl_value_t addrspace(10)** %1, %jl_value_t addrspace(10)*** %5, align 8
%thread_ptr = call i8* asm "movq %fs:0, $0", "=r"()
%ptls_i8 = getelementptr i8, i8* %thread_ptr, i64 -10920
%ptls = bitcast i8* %ptls_i8 to %jl_value_t***
%6 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %gcframe, i32 0
%7 = bitcast %jl_value_t addrspace(10)** %6 to i64*
store i64 4, i64* %7
%8 = getelementptr %jl_value_t**, %jl_value_t*** %ptls, i32 0
%9 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %gcframe, i32 1
%10 = bitcast %jl_value_t addrspace(10)** %9 to %jl_value_t***
%11 = load %jl_value_t**, %jl_value_t*** %8
store %jl_value_t** %11, %jl_value_t*** %10
%12 = bitcast %jl_value_t*** %8 to %jl_value_t addrspace(10)***
store %jl_value_t addrspace(10)** %gcframe, %jl_value_t addrspace(10)*** %12
%13 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 0
store %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958353891376 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %13
%14 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 1
store %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958353891392 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %14
%15 = call nonnull %jl_value_t addrspace(10)* @jsys1_vect_30114(%jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958473544592 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %3, i32 2)
%16 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %gcframe, i32 3
store %jl_value_t addrspace(10)* %15, %jl_value_t addrspace(10)** %16
%17 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 0
store %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958353891408 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %17
%18 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 1
store %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958353891424 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %18
%19 = call nonnull %jl_value_t addrspace(10)* @jsys1_vect_30114(%jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958473544592 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %3, i32 2)
%20 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %gcframe, i32 2
store %jl_value_t addrspace(10)* %19, %jl_value_t addrspace(10)** %20
%21 = call [1 x { i64 }] @julia_promote_shape_36014(%jl_value_t addrspace(10)* nonnull %15, %jl_value_t addrspace(10)* nonnull %19)
%22 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 0
store %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958447711088 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %22
%23 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 1
store %jl_value_t addrspace(10)* %15, %jl_value_t addrspace(10)** %23
%24 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %3, i32 2
store %jl_value_t addrspace(10)* %19, %jl_value_t addrspace(10)** %24
%25 = call nonnull %jl_value_t addrspace(10)* @japi1_broadcast_36015(%jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 139958447688464 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(10)** %3, i32 3)
%26 = getelementptr %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %gcframe, i32 1
%27 = load %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %26
%28 = getelementptr %jl_value_t**, %jl_value_t*** %ptls, i32 0
%29 = bitcast %jl_value_t*** %28 to %jl_value_t addrspace(10)**
store %jl_value_t addrspace(10)* %27, %jl_value_t addrspace(10)** %29
ret %jl_value_t addrspace(10)* %25
}
しかしこれをllcで処理しようとすると
$ llc -march=nvptx64 -mcpu=sm_50 add.ll
llc: add.ll:4:16: error: use of undefined type named 'jl_value_t'
define nonnull %jl_value_t addrspace(10)* @japi1_main_36013(%jl_value_t addrspace(10)*, %jl_value_t addrspace(10)**, i32) #0 {
のように定義が足りてないようです。どうすればコンパイルできるIRを得ることができますか?
- julia version 1.0.0
- LLVM version 6.0.1