2019年01月18日
Xilinx QEMU上でToppersを動かしてみる(RPU、APU+RPU編)
前回の記事では、Xilinx QEMU の Zynq UltraScale+ MPSoC ZCU102(ZynqMP)ターゲットの APU(AArch64 Cortex-A53 4 コア)上で Toppers fmp を動かしました。
今回は RPU(ARM Cortex-R5 2 コア)上で Toppers fmp を動かして見ます。
環境は前回の準備を前提としますが、今度は ARM のツールチェーンの準備が別途必要です。
今回は RPU(ARM Cortex-R5 2 コア)上で Toppers fmp を動かして見ます。
環境は前回の準備を前提としますが、今度は ARM のツールチェーンの準備が別途必要です。
当初は APU と同じように Linaro のツールをダウンロードしてビルドしてみたのですが、明らかにツールチェーンの名前が異なったり、ちょこちょこ修正が必要だったのでドキュメント(fmp_1.4.0/target/zynqmp_r5_gcc/target_user.txt)を探して調べて見ると、APU も RPU も Xilinx SDK に付属のツールチェーンでビルドすることが前提であったことに気付きました。
このビルド環境の Ubuntu は基本 ssh で使っているので、GUI が必要な Xilinx の SDK(Linux 版)をインストールするのは実機まで行かないといけないのでけっこう面倒だったのですが、一応正式なビルド手順も試してみました。
というわけで前置きが長くなりましたが、Linaro 版と Xilinx SDK 版の両方のビルド手順を解説します。少々修正が面倒ですが、Linaro 版の方がサクッと ssh のみで準備ができるので個人的には好みです。Xilinx SDK は Xilinx のアカウント作成が必要ですし。
また、せっかくなので、Xilinx SDK(Xilinx アカウント)が一切不要なように、自前で dtb ファイル(Xilinx QEMU の仮想 H/W 構成を設定するための、バイナリ形式の設定ファイル)をビルドして使ってみます。
〇 作業ディレクトリの作成と Toppers ソースの入手、cfg の準備(共通)
cfg は前回の APU の所からコピーしました。
〇 Linaro のツールでのビルド
ツールを wget して PATH を通します。
〇 Xilinx SDK でのビルド
Xilinx SDK をインストールします。インストーラの入手にも、インストールにも Xilinx アカウントが必須なので、wget はできません。以下の URL をブラウザで開いて、必要な項目を入力してください。
https://japan.xilinx.com/member/forms/download/xef.html?filename=Xilinx_SDK_2018.3_1207_2324_Lin64.bin
最初から実行権が付いていたので、chmod +x は不要でした。GUI 環境で実行しないと、X Display がオープンできないとエラーになります。他には Java ランタイム等が必要のようですが、私の Ubuntu 環境では特に何もインストールしなくても実行できました。
〇 dtb のビルド
たぶんこの QEMU がビルドできる環境ならば既にインストール済みだと思いますが、dtc(Device Tree Compiler)が必要です。また、GCC のプリプロセッサを使っているので、ターゲットは何でも良いので GCC が必要です。
〇 動作確認
APU と違ってネット上に情報が全然無いので苦労しました。(私は Toppers の開発者である、名古屋大学の本田晋也先生にメールで問い合わせて教えていただきました。)
https://www.xilinx.com/support/documentation/sw_manuals/xilinx2018_2/ug1169-xilinx-qemu.pdf
ARM の R コアの特徴的な機能として、システムに冗長性を持たせるためにデュアルコアで全く同じプログラムを動作させ、その結果が同じ場合のみ実行する(ノイズなどによる誤作動防止)ロックステップモードがあるようですが、今回は 2 コアを普通に動かすモードにしてみました。
私がかなりハマった点として、APU の場合は何もオプションを渡さなくても syslog() 出力がコマンドプロンプトに出たのですが、RPU の場合は APU とは異なる方のシリアルに出力するようで、デフォルトでは何も出ないという挙動です。-serial mon:stdio -serial mon:stdio と、両方のシリアルをコマンドプロンプトに出す必要がありました。
以下は Xilinx SDK でビルドしたものですが、Linaro も同じ動作だと思います。(簡単にしか動作確認してませんが…。)
APU と RPU を同時に動かすこともできるようです。表示がぐちゃぐちゃになってしまいますが。
このビルド環境の Ubuntu は基本 ssh で使っているので、GUI が必要な Xilinx の SDK(Linux 版)をインストールするのは実機まで行かないといけないのでけっこう面倒だったのですが、一応正式なビルド手順も試してみました。
というわけで前置きが長くなりましたが、Linaro 版と Xilinx SDK 版の両方のビルド手順を解説します。少々修正が面倒ですが、Linaro 版の方がサクッと ssh のみで準備ができるので個人的には好みです。Xilinx SDK は Xilinx のアカウント作成が必要ですし。
また、せっかくなので、Xilinx SDK(Xilinx アカウント)が一切不要なように、自前で dtb ファイル(Xilinx QEMU の仮想 H/W 構成を設定するための、バイナリ形式の設定ファイル)をビルドして使ってみます。
〇 作業ディレクトリの作成と Toppers ソースの入手、cfg の準備(共通)
cfg は前回の APU の所からコピーしました。
$ mkdir -p test/fmp/arm $ cd test/fmp/arm $ wget https://www.toppers.jp/download.cgi/fmp_zynqmp_r5_gcc-20180713.zip $ unzip fmp_zynqmp_r5_gcc-20180713.zip $ cp ../aarch64/fmp_1.4.0/cfg/cfg/cfg fmp_1.4.0/cfg/cfg/ $ ls fmp_1.4.0/cfg/cfg/ cfg cfg.exe $ cd fmp_1.4.0/ $ mkdir OBJ $ cd OBJ以下のビルドは、どちらか一方だけで大丈夫です。
〇 Linaro のツールでのビルド
ツールを wget して PATH を通します。
$ wget https://releases.linaro.org/components/toolchain/binaries/latest-7/arm-eabi/gcc-linaro-7.3.1-2018.05-x86_64_arm-eabi.tar.xz $ tar xvf gcc-linaro-7.3.1-2018.05-x86_64_arm-eabi.tar.xz $ export PATH=/home/kmc/test/fmp/arm/gcc-linaro-7.3.1-2018.05-x86_64_arm-eabi/bin/:$PATH $ arm-eabi-gcc -v 。。。 gcc バージョン 7.3.1 20180425 [linaro-7.3-2018.05 revision d29120a424ecfbc167ef90065c0eeb7f91977701] (Linaro GCC 7.3-2018.05)ツールチェーンの名前を修正します。
$ vim ../target/zynqmp_r5_gcc/Makefile.target -GCC_TARGET = armr5-none-eabi +GCC_TARGET = arm-eabiそのまま configure して make すると、以下のようなエラーが出ます。
$ perl ../configure -T zynqmp_r5_gcc $ make 。。。 ../target/zynqmp_r5_gcc/target_config.c: 関数 ‘_kernel_target_initialize’ 内: ../target/zynqmp_r5_gcc/target_config.c:306:2: エラー: #error Only support G_SYSLOG #error Only support G_SYSLOG ^~~~~ Makefile:518: recipe for target 'obj/target_config.o' failed make: *** [obj/target_config.o] Error 1一度 clean し、前述したドキュメントに従って Makefile を修正し、make します。
$ make clean $ vim Makefile -ENABLE_G_SYSLOG = +ENABLE_G_SYSLOG = true $ makeすると今度は以下のようなエラーが出ます。
/home/kmc/test/fmp/arm/gcc-linaro-7.3.1-2018.05-x86_64_arm-eabi/bin/../lib/gcc/arm-eabi/7.3.1/../../../../arm-eabi/bin/ld: section .note.gnu.build-id LMA [0000000000000000,0000000000000023] overlaps section .vector LMA [0000000000000000,000000000000003b]よくわかりませんでしたが、.note.gnu.build-id セクションはたぶん不要なので、生成しないようにして回避しました。
$ make clean $ LDFLAGS="-Wl,--build-id=none" make
〇 Xilinx SDK でのビルド
Xilinx SDK をインストールします。インストーラの入手にも、インストールにも Xilinx アカウントが必須なので、wget はできません。以下の URL をブラウザで開いて、必要な項目を入力してください。
https://japan.xilinx.com/member/forms/download/xef.html?filename=Xilinx_SDK_2018.3_1207_2324_Lin64.bin
最初から実行権が付いていたので、chmod +x は不要でした。GUI 環境で実行しないと、X Display がオープンできないとエラーになります。他には Java ランタイム等が必要のようですが、私の Ubuntu 環境では特に何もインストールしなくても実行できました。
./Xilinx_SDK_2018.3_1207_2324_Lin64.bin/home/kmc/xilinx/tool にインストールしました。
$ export PATH=/home/kmc/xilinx/tool/SDK/2018.3/gnu/armr5/lin/gcc-arm-none-eabi/bin/:$PATH $ armr5-none-eabi-gcc -v 。。。 gcc version 7.3.1 20180314 (GNU Tools for ARM Embedded Processors)G_SYSLOG の設定は Linaro 同様に必要ですが、他はそのまま行けます。
$ perl ../configure -T zynqmp_r5_gcc $ vim Makefile -ENABLE_G_SYSLOG = +ENABLE_G_SYSLOG = true $ make
〇 dtb のビルド
たぶんこの QEMU がビルドできる環境ならば既にインストール済みだと思いますが、dtc(Device Tree Compiler)が必要です。また、GCC のプリプロセッサを使っているので、ターゲットは何でも良いので GCC が必要です。
$ sudo apt-get install device-tree-compiler 。。。 device-tree-compiler はすでに最新バージョン (1.4.5-3) です。 $ git clone https://github.com/Xilinx/qemu-devicetrees.git $ cd qemu-devicetrees/ $ make新規作成される LATEST/ 以下に dtb ができています。
〇 動作確認
APU と違ってネット上に情報が全然無いので苦労しました。(私は Toppers の開発者である、名古屋大学の本田晋也先生にメールで問い合わせて教えていただきました。)
https://www.xilinx.com/support/documentation/sw_manuals/xilinx2018_2/ug1169-xilinx-qemu.pdf
ARM の R コアの特徴的な機能として、システムに冗長性を持たせるためにデュアルコアで全く同じプログラムを動作させ、その結果が同じ場合のみ実行する(ノイズなどによる誤作動防止)ロックステップモードがあるようですが、今回は 2 コアを普通に動かすモードにしてみました。
私がかなりハマった点として、APU の場合は何もオプションを渡さなくても syslog() 出力がコマンドプロンプトに出たのですが、RPU の場合は APU とは異なる方のシリアルに出力するようで、デフォルトでは何も出ないという挙動です。-serial mon:stdio -serial mon:stdio と、両方のシリアルをコマンドプロンプトに出す必要がありました。
以下は Xilinx SDK でビルドしたものですが、Linaro も同じ動作だと思います。(簡単にしか動作確認してませんが…。)
> install\qemu-system-aarch64.exe -nographic -M arm-generic-fdt -dtb u:\qemu-devicetrees/LATEST/SINGLE_ARCH/zcu102-arm.dtb -device loader,addr=0xff5e023c,data=0x80008fdc,data-len=4 -device loader,addr=0xff9a0000,data=0x80000218,data-len=4 -device loader,file=u:\test\fmp\arm\fmp_1.4.0\OBJ\fmp,cpu-num=4 -device loader,file=u:\test\fmp\arm\fmp_1.4.0\OBJ\fmp,cpu-num=5 -serial null -serial mon:stdio TOPPERS/FMP Kernel Release 1.4.0 for ZYNQMP_R5(Cortex-R5F) (Jan 18 2019, 11:15:56) Copyright (C) 2000-2003 by Embedded and Real-Time Systems Laboratory Toyohashi Univ. of Technology, JAPAN Copyright (C) 2004-2015 by Embedded and Real-Time Systems Laboratory Graduate School of Information Science, Nagoya Univ., JAPAN Processor 1 start. local_inirtn exinf = 1, counter = 1 System logging task is started on port 1. Server task 1 starts. Sample program starts (exinf = 1). select tskno 0x11 select cycid 1 select almid 1 select processor 1 select class 1 task1_1 is running (001). | task1_1 is running (002). | task1_1 is running (003). | task1_1 is running (004). | task1_1 is running (005). | task1_1 is running (006). | 。。。どうも 1 タスクしか動いていない感じなのが気になりますが…とりあえず良しとします。
APU と RPU を同時に動かすこともできるようです。表示がぐちゃぐちゃになってしまいますが。
> install\qemu-system-aarch64.exe -nographic -M arm-generic-fdt -dtb u:\qemu-devicetrees/LATEST/SINGLE_ARCH/zcu102-arm.dtb -device loader,file=u:\test\fmp\aarch64\fmp_1.4.0\OBJ\fmp,cpu-num=0 -device loader,addr=0xfd1a0104,data=0x8000000e,data-len=4 -device loader,addr=0xff5e023c,data=0x80008fdc,data-len=4 -device loader,addr=0xff9a0000,data=0x80000218,data-len=4 -device loader,file=u:\test\fmp\arm\fmp_1.4.0\OBJ\fmp,cpu-num=4 -device loader,file=u:\test\fmp\arm\fmp_1.4.0\OBJ\fmp,cpu-num=5 -serial mon:stdio -serial mon:stdio Processor 2 start. TOPPERS/FMP Kernel Release 1.4 .0 for ZYNQMP_R5(Cortex-R5F) (Jan 18 2019, 11:15:56) Copyright (C) 2000-2003 by EmbeddedP and Real-Time Systems Larocessor 3 start. Processor 4 start. boratory Toyohashi Univ. of Technology, JAPAN Copyright (C) 2004-2015 by Embedded and Real-Time Systems Laboratory Graduate School of Information Science, Nagoya Univ., JAPAN TOPPERS/FMP Kernel Release 1. Processor 1 start. local_inirtn exinf = 1, counter = 14 .0 for Xilinx ZynqMP A53(AArch64 Secure) (Jan 7 2019, 18:34:08) Copyright (C) 2000-2003 by Embedded and Real-Time Systems Laboratory Toyohashi Univ. of Technology, JAPAN Copyright (C) 2004-2015 by Embedded and Real-Time Systems Laboratory Graduate School of Information Science, Nagoya Univ., JAPAN local_inirtn exinf = 2, counter = 1 local_inirtn exinf = 3, counter = 2 Processor 1 start. local_inirtn exinf = 1, counter = 4 local_inirtn exinf = 4, counter = 3 Server task 3 starts. Server task 2 starts. Server task 4 starts. System logging task is started on port 1. System logging task is started on port 1. Server task 1 starts. Sample program starts (exinf = 1). select tskno 0x11 select cycid 1 select almid 1 select processor 1 select class 1 task1_1 is running (001). | Server task 1 starts. Sample program starts (exinf = 1). select tskno 0x11 select cycid 1 select almid 1 select processor 1 select class 1 task1_1 is running (001). | task1_1 is running (002). | task1_1 is running (003). | task1_1 is running (002). | task1_1 is running (004). | task1_1 is running (005). | task1_1 is running (006). | task1_1 is running (007). | task1_1 is running (003). | 。。。ちなみに、正しく終了させる方法がよくわからないので、Ctrl + C で強制終了しています。