LLVMについて理解するために、RISC-Vをネタにしていろいろ勉強してみたい。 Release 7.0では一応RISC-Vの32-bitと64-bit版がサポートされているようなので、ビルドに追加して様子を見てみる。
$ cmake -G Ninja -DCMAKE_BUILD_TYPE="Debug" -DLLVM_TARGETS_TO_BUILD="Cpu0" -DLLVM_EXPERIMENTAL_TARGETS_TO_BUILD="RISCV" ../llvm-msyksphinz $ cmake --build .
まずは、32‐bitと64‐bitで単純な関数をビルドして様子を見る。LLVM Backend tutorialに出てくるch3_1.cppをビルドして様子を見る。
ch3_1.cpp
int main() { return 0; }
- GCCの場合
$ riscv64-unknown-elf-gcc -c ../lbdex/input/ch3.cpp $ riscv64-unknown-elf-objdump -d ch3.o ch3.o: file format elf64-littleriscv Disassembly of section .text: 0000000000000000 <main>: 0: 1141 addi sp,sp,-16 2: e422 sd s0,8(sp) 4: 0800 addi s0,sp,16 6: 4791 li a5,4 8: 853e mv a0,a5 a: 6422 ld s0,8(sp) c: 0141 addi sp,sp,16 e: 8082 ret
- LLVMの場合(32-bit)
$ ./bin/clang -target riscv32-unknown-linux-gnu -c ../lbdex/input/ch3.cpp -emit-llvm -o ch3.riscv32.bc $ ./bin/llvm-dis ch3.riscv32.bc -o -
; ModuleID = 'ch3.riscv32.bc' source_filename = "../lbdex/input/ch3.cpp" target datalayout = "e-m:e-p:32:32-i64:64-n32-S128" target triple = "riscv32-unknown-linux-gnu" ; Function Attrs: noinline norecurse nounwind optnone define dso_local i32 @main() #0 { entry: %retval = alloca i32, align 4 store i32 0, i32* %retval, align 4 ret i32 0 }
$ ./bin/llc -march=riscv32 -relocation-model=pic -filetype=asm ch3.riscv32.bc -o -
main: # @main # %bb.0: # %entry addi sp, sp, -16 sw ra, 12(sp) sw s0, 8(sp) addi s0, sp, 16 sw zero, -12(s0) mv a0, zero lw s0, 8(sp) lw ra, 12(sp) addi sp, sp, 16 ret
- LLVMの場合(64-bit)
$ ./bin/clang -target riscv64-unknown-linux-gnu -c ../lbdex/input/ch3.cpp -emit-llvm -o ch3.riscv64.bc $ ./bin/llvm-dis ch3.riscv64.bc -o - ; ModuleID = 'ch3.riscv64.bc' source_filename = "../lbdex/input/ch3.cpp" target datalayout = "e-m:e-p:64:64-i64:64-i128:128-n64-S128" target triple = "riscv64-unknown-linux-gnu" ; Function Attrs: noinline norecurse nounwind optnone define dso_local signext i32 @main() #0 { entry: %retval = alloca i32, align 4 store i32 0, i32* %retval, align 4 ret i32 4 }
$ ./bin/llc -march=riscv64 -relocation-model=pic -filetype=asm ch3.riscv64.bc -o - .text .file "ch3.cpp" LLVM ERROR: Cannot select: t12: ch = store<(store 4 into %ir.retval), trunc to i32> t0, Constant:i64<0>, FrameIndex:i64<0>, undef:i64 t11: i64 = Constant<0> t2: i64 = FrameIndex<0> t4: i64 = undef In function: main
うーん、何故か64-bitでllcを実行すると落ちてしまう。どこかDAGが足りていないのか?解析するのにはどうしたらいいんだ?