FPGA開発日記

カテゴリ別記事インデックス https://msyksphinz.github.io/github_pages , English Version https://fpgadevdiary.hatenadiary.com/

RISC-V Getting Started GuideのLinuxビルドを試す

f:id:msyksphinz:20200503214338p:plain

RISC-V Getting Started Guideというページがある。目的ベースで、QEMULinuxなどのオペレーティングシステムを動かすための方法や、様々なツールキットを動かすための情報がまとめられている。

risc-v-getting-started-guide.readthedocs.io

ここに"Running 64- and 32-bit RISC-V Linux on QEMU" という項目がある。これまでFreedom-u-sdkのツールキットを使うしか方法が無いのかと思っていたが、どうやら別の方法を使ってQEMULinuxをブートできるらしい。やってみよう。

risc-v-getting-started-guide.readthedocs.io

前提としてriscv64-unknown-elf-gccriscv64-unknown-linux-gnu-gccがビルドできる状態であること。 フローの中にはricsv-gnu-toolchainをダウンロードしてこれらのビルドを行うステップも含まれているが、ネットワーク帯域が必要だしビルドも時間がかかるので、私はすでにビルドしてある自前のツールを使って省略。

Getting the sourcesから始める。

# すでにビルドしてあるものを使用するためriscv-gnu-toolchainは使用しない
# git clone --recursive https://github.com/riscv/riscv-gnu-toolchain
git clone https://github.com/qemu/qemu
git clone https://github.com/torvalds/linux
git clone https://github.com/riscv/riscv-pk
git clone https://github.com/michaeljclark/busybear-linux

まずはQEMUのビルドから。これはフローに乗るだけで問題なくビルドできた。sudo make installがしたくないので、prefix=を設定してホーム領域中にインストールしておく。

cd qemu
git checkout v3.0.0
./configure --target-list=riscv64-softmmu --prefix=${HOME}/riscv-linux-toolkit
make -j $(nproc)
make install

次はLinuxのビルドとなる。これもフローに則って行う。

cd linux
git checkout v4.19-rc3
cp ../busybear-linux/conf/linux.config .config
make ARCH=riscv CROSS_COMPILE=riscv64-unknown-linux-gnu- olddefconfig

カーネルのコンフィグレーションは特に変更せずに特に設定は適用されていた。

make ARCH=riscv CROSS_COMPILE=riscv64-unknown-linux-gnu- nconfig

.configで以下のパラメータが設定されていることを確認する。

ARCH_RV64I
CMODEL_MEDANY
CONFIG_SIFIVE_PLIC

ビルドを実行する。

make ARCH=riscv CROSS_COMPILE=riscv64-unknown-linux-gnu- vmlinux -j $(nproc)

次はBBL(Berkeley Boot Loader)のビルドを行う。BBLはブートローダなのだが、ブートローダによるセットアップが終わった後にvmlinuxを起動するという要領だ。

cd riscv-pk
mkdir build && cd build
../configure --enable-logo --host=riscv64-unknown-elf --with-payload=../../linux/vmlinux
make -j $(nproc)

最後にファイルシステムの用意だ。Busybear Linuxのビルドを行う。

cd busybear-linux
make -j $(nproc)

あれ、途中でビルドが止まってしまった。

  KSYM    .tmp_kallsyms2.o
  LD      vmlinux
  SYSMAP  System.map
make[1]: Leaving directory '/home/msyksphinz/work/riscv/riscv-linux-kit/busybear-linux/build/linux-5.0'
./scripts/build.sh: line 84: ../../src/riscv-pk/configure: No such file or directory
make: *** [Makefile:10: busybear.bin] Error 127
zsh: exit 2     make -j$(nproc)
DESKTOP-P42Q0NR:busybear-linux msyksphinz$

色々調べると、なんだ、busybear-linuxにはひそかにsubmodulesが含まれているじゃないか。

git submodule update --init --recusive

再度ビルドに挑戦する。

In file included from /home/msyksphinz/riscv64-ctng-linux/riscv64-unknown-linux-gnu/sysroot/usr/include/features.h:474,
                 from /home/msyksphinz/riscv64-ctng-linux/riscv64-unknown-linux-gnu/sysroot/usr/include/sys/stat.h:25,
                 from ../../src/riscv-pk/pk/file.h:6,
                 from ../../src/riscv-pk/pk/file.c:3:
/home/msyksphinz/riscv64-ctng-linux/riscv64-unknown-linux-gnu/sysroot/usr/include/gnu/stubs.h:8:11: fatal error: gnu/stubs-lp64.h: No such file or directory
 # include <gnu/stubs-lp64.h>
           ^~~~~~~~~~~~~~~~~~

次はこんな感じのエラーで怒られた。gnu/stubs-lp64.hが無い? 渡しのriscv64-unknown-linux-gnuはcrostools-ngでビルドしたものだ。これだと問題が発生するのだろうか?

以下のIssueを見ながら、とりあえず既存のstubs-lp64d.hstubs-lp64.hにコピーした。

sudo cp ./riscv64-unknown-linux-gnu/sysroot/usr/include/gnu/stubs-lp64d.h ./riscv64-unknown-linux-gnu/sysroot/usr/include/gnu/stubs-lp64.h

さらに進めると今度は謎のエラーだ。なんだこれは。。。

riscv64-unknown-linux-gnu-ranlib libsoftfloat.a
riscv64-unknown-linux-gnu-gcc -Wl,--build-id=none -nostartfiles -nostdlib -static  -march=rv64gc -mabi=lp64 -o pk pk.o -L.  -lpk  -lmachine  -lsoftfloat  -lutil -lgcc -T ../../src/riscv-pk/pk/pk.lds
riscv64-unknown-linux-gnu-gcc -Wl,--build-id=none -nostartfiles -nostdlib -static  -march=rv64gc -mabi=lp64 -o bbl bbl.o -L.  -lbbl  -ldummy_payload  -lmachine  -lsoftfloat  -lutil -lgcc -T ../../src/risc
v-pk/bbl/bbl.lds
make[1]: Leaving directory '/home/msyksphinz/work/riscv/riscv-linux-kit/busybear-linux/build/riscv-pk'
[sudo] password for msyksphinz:
env: 'Files/PuTTY:/mnt/c/Program': No such file or directory
make: *** [Makefile:10: busybear.bin] Error 127

これはどうもWSL特有の問題らしい。PATHに変な文字列が入っているのがおかしいようなので、PATHに通すディレクトリを限定して再度試行する。

100+0 records in
100+0 records out
104857600 bytes (105 MB, 100 MiB) copied, 0.0597549 s, 1.8 GB/s
mke2fs 1.44.4 (18-Aug-2018)
Creating filesystem with 102400 1k blocks and 25688 inodes
Filesystem UUID: e992d615-9ab7-470d-b78e-6b980fffb641
Superblock backups stored on blocks:
        8193, 24577, 40961, 57345, 73729

Allocating group tables: done
Writing inode tables: done
Creating journal (4096 blocks): done
Writing superblocks and filesystem accounting information: done

mount: mnt: mount failed: Operation not permitted.
make: *** [Makefile:10: busybear.bin] Error 1
zsh: exit 2     make -j$(nproc)

最後はエラーで止まったが、目標のbusybear.binは生成されたようなのでさっそくQEMUで実行してみよう。

~/riscv-linux-kit/bin/qemu-system-riscv64 -nographic -machine virt \
     -kernel riscv-pk/build/bbl -append "root=/dev/vda ro console=ttyS0" \
     -drive file=busybear-linux/busybear.bin,format=raw,id=hd0 \
     -device virtio-blk-device,drive=hd0
bbl loader
              vvvvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
                  vvvvvvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrr       vvvvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrrrrr      vvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrrrrrrr    vvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrrrrrrr    vvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrrrrrrr    vvvvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrrrrr      vvvvvvvvvvvvvvvvvvvvvv
rrrrrrrrrrrrr       vvvvvvvvvvvvvvvvvvvvvv
rr                vvvvvvvvvvvvvvvvvvvvvv
rr            vvvvvvvvvvvvvvvvvvvvvvvv      rr
rrrr      vvvvvvvvvvvvvvvvvvvvvvvvvv      rrrr
rrrrrr      vvvvvvvvvvvvvvvvvvvvvv      rrrrrr
rrrrrrrr      vvvvvvvvvvvvvvvvvv      rrrrrrrr
rrrrrrrrrr      vvvvvvvvvvvvvv      rrrrrrrrrr
rrrrrrrrrrrr      vvvvvvvvvv      rrrrrrrrrrrr
rrrrrrrrrrrrrr      vvvvvv      rrrrrrrrrrrrrr
rrrrrrrrrrrrrrrr      vv      rrrrrrrrrrrrrrrr
rrrrrrrrrrrrrrrrrr          rrrrrrrrrrrrrrrrrr
rrrrrrrrrrrrrrrrrrrr      rrrrrrrrrrrrrrrrrrrr
rrrrrrrrrrrrrrrrrrrrrr  rrrrrrrrrrrrrrrrrrrrrr

       INSTRUCTION SETS WANT TO BE FREE
[    0.000000] OF: fdt: Ignoring memory range 0x80000000 - 0x80200000
[    0.000000] Linux version 4.19.0-rc3 (msyksphinz@DESKTOP-P42Q0NR) (gcc version 8.3.0 (crosstool-NG 1.24.0)) #1 SMP Sun May 3 19:13:43 JST 2020
[    0.000000] bootconsole [early0] enabled
[    0.000000] Initial ramdisk at: 0x(____ptrval____) (512 bytes)
[    0.000000] Zone ranges:
[    0.000000]   DMA32    empty
[    0.000000]   Normal   [mem 0x0000000080200000-0x0000000087ffffff]
[    0.000000] Movable zone start for each node
[    0.000000] Early memory node ranges
[    0.000000]   node   0: [mem 0x0000000080200000-0x0000000087ffffff]
[    0.000000] Initmem setup node 0 [mem 0x0000000080200000-0x0000000087ffffff]
[    0.000000] software IO TLB: mapped [mem 0x83e3d000-0x87e3d000] (64MB)
[    0.000000] elf_hwcap is 0x112d
[    0.000000] percpu: Embedded 16 pages/cpu @(____ptrval____) s25496 r8192 d31848 u65536
[    0.000000] Built 1 zonelists, mobility grouping on.  Total pages: 31815
[    0.000000] Kernel command line: root=/dev/vda ro console=ttyS0

ブートは始まったようだが、しばらくすると止まってしまった。うーん、やはりWSLでビルドしたのが良くないのだろうか...?

[    0.592000] Run /bin/init as init process
[    0.592000] Run /bin/sh as init process
[    0.592000] Kernel panic - not syncing: No working init found.  Try passing init= option to kernel. See Linux Documentation/admin-guide/init.rst for guidance.
[    0.592000] CPU: 0 PID: 1 Comm: swapper/0 Not tainted 4.19.0-rc3 #1
[    0.592000] Call Trace:
[    0.592000] [<ffffffe00002825c>] walk_stackframe+0x0/0xa0
[    0.592000] [<ffffffe0000283bc>] show_stack+0x2a/0x34
[    0.592000] [<ffffffe0003376f4>] dump_stack+0x62/0x7c
[    0.592000] [<ffffffe00002c31a>] panic+0xd2/0x1e8
[    0.592000] [<ffffffe0003489d8>] kernel_init+0xe4/0xf0
[    0.592000] [<ffffffe0000272ee>] ret_from_exception+0x0/0xc

カーネルパニックを起こしてしまった。これが問題なのかが分からないので、純粋なUbuntuの環境を作成して試行してみよう。