Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Zynq+PyCoRAM(+Debian)入門

5,899 views

Published on

Zynq+PyCoRAM(+Debian)入門

Published in: Technology
  • Be the first to comment

Zynq+PyCoRAM(+Debian)入門

  1. 1. Zynq + PyCoRAM (+Debian) 入門 高前田 伸也 奈良先端科学技術大学院大学 情報科学研究科 E-mail: shinya_at_is_naist_jp
  2. 2. チュートリアルの目的 n  「Zynq+Vivado HLS入門」や「Zynq+Synthesijer入門」 と同様にZynq上でPyCoRAMで生成したIPコアを用いた HW/SWシステムを動作させる方法を習得する l  ZynqにIPコアを組み込みDebian Linux上から利用します n  ターゲットボード: ZedBoard l  ZC706なども適宜読み替えれば同様の手順で可能 n  開発環境: Ubuntu (64-bit) 14.04 LTS n  PyCoRAMを利用するためにPythonなどが必要です l  Linuxの利用を推奨 n  主な流れは 「Zynq+Vivado HLS入門」「Zynq+Synthesijer入門」と にならっています 2015-03-19 Shinya T-Y, NAIST 2
  3. 3. ゴールのシステム構成 n  メモリコピーを行うハードウェアをARMから利用する l  ARM上のソフトウェアでDRAM上に初期値を設定 l  IPコアがDRAMからデータを読み込み宛先領域に書き戻す l  ARM上のソフトウェアで正しくコピーされたかどうか確認する n  Debian Linuxを利用するリッチなシステム l  OSによるメモリ管理が存在 l  一部メモリ領域をLinux 管理外として割り当て mmapを介して利用 •  PL側は仮想アドレスでは メモリアクセスできない •  連続する物理メモリ空間を PL側に割り当てる 2015-03-19 Shinya T-Y, NAIST 3 PS ARM L1 L2 DRAM I/F PL PyCoRAM IP (memcpy) DRAM HP0GP0 Zynq
  4. 4. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 4 PyCoRAMによる開発 VivadoによるFPGAハードウェア開発 Linuxのビルド 実機検証
  5. 5. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 5
  6. 6. Icarus Verilog・Python関連のインストール n  apt-getでインストール n  pipでjinja2(テンプレートエンジン)をインストール 2015-03-19 Shinya T-Y, NAIST 6 sudo apt-get install iverilog gtkwave python3 python3-pip� pip3 install jinja2�
  7. 7. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 7
  8. 8. PyCoRAM/Pyverilogのダウンロード n  開発用ディレクトリを作成し そこにPyCoRAMをGitHubからダウンロード n  PyCoRAMの中にPyverilogをダウンロードし さらにpycoramの中にシンボリックリンクを作成 2015-03-19 Shinya T-Y, NAIST 8 mkdir -p ~/work� cd ~/work� git clone https://github.com/shtaxxx/PyCoRAM.git� cd PyCoRAM� git clone https://github.com/shtaxxx/Pyverilog.git� cd pycoram� ln -s ../Pyverilog/pyverilog� cd ../�
  9. 9. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 9
  10. 10. memcpyをコンパイルしてみる n  おなじみのmemcpyの例を試してみる n  “PyCoRAM/sample/test/memcpy”へ移動しmake build n  “pycoram_userlogic_v1_00_a”というpcore/IP-XACT 両対応のIPコアのディレクトリが作成される n  中身が気になる方は”ctrl_thread.py”とuserlogic.vを確認 2015-03-19 Shinya T-Y, NAIST 10 cd sample/test/memcpy� make build� ls� less ctrl_thread.py� less userlogic.v�
  11. 11. userlogic.v 2015-03-19 Shinya T-Y, NAIST 11 `include "pycoram.v"� � `define THREAD_NAME "ctrl_thread"� � module userlogic # � (� parameter W_A = 10,� parameter W_D = 32,� parameter W_COMM_A = 4� )� (� input CLK,� input RST� );� � reg [W_A-1:0] mem_addr;� reg [W_D-1:0] mem_d;� reg mem_we;� wire [W_D-1:0] mem_q;� � reg [W_D-1:0] comm_d;� reg comm_enq;� wire comm_full;� wire [W_D-1:0] comm_q;� reg comm_deq;� wire comm_empty;� � always @(posedge CLK) begin� if(RST) begin� mem_addr <= 0;� mem_d <= 0;� mem_we <= 0;� comm_d <= 0;� comm_deq <= 0;� comm_enq <= 0;� end else begin� // do nothing� mem_addr <= 0;� mem_d <= 0;� mem_we <= 0;� comm_d <= 0;� comm_deq <= 0;� comm_enq <= 0;� end� end� CoramMemory1P� #(� .CORAM_THREAD_NAME(`THREAD_NAME),� .CORAM_ID(0),� .CORAM_SUB_ID(0),� .CORAM_ADDR_LEN(W_A),� .CORAM_DATA_WIDTH(W_D)� )� inst_data_memory� (.CLK(CLK),� .ADDR(mem_addr),� .D(mem_d),� .WE(mem_we),� .Q(mem_q)� );� � CoramChannel� #(� .CORAM_THREAD_NAME(`THREAD_NAME),� .CORAM_ID(0),� .CORAM_ADDR_LEN(W_COMM_A),� .CORAM_DATA_WIDTH(W_D)� )� inst_comm_channel� (.CLK(CLK),� .RST(RST),� .D(comm_d),� .ENQ(comm_enq),� .FULL(comm_full),� .Q(comm_q),� .DEQ(comm_deq),� .EMPTY(comm_empty)� );� � endmodule� � 何もしないハードウェア (メモリがあるだけ) メモリコピーの振る舞いは Python側で記述 (そもそもPython側の 仕事がDMA転送の管理)
  12. 12. ctrl_thread.py 2015-03-19 Shinya T-Y, NAIST 12 DSIZE = 4 # = 32 bit� RAMSIZE = 1024� � iochannel = CoramIoChannel(idx=0, datawidth=32)� ram = CoramMemory(idx=0, datawidth=DSIZE*8, size=RAMSIZE, length=1, scattergather=False)� channel = CoramChannel(idx=0, datawidth=32, size=16) # Unused� � def body():� # wait request� src = iochannel.read()� dst = iochannel.read()� size = iochannel.read()� � while True:� chunk_size = size if size < RAMSIZE * DSIZE else RAMSIZE * DSIZE� ram.write(0, src, chunk_size/DSIZE) # from DRAM to BlockRAM� ram.read(0, dst, chunk_size/DSIZE) # from BlockRAM to DRAM� size -= chunk_size� src += chunk_size� dst += chunk_size� if size == 0: break� � # notification� iochannel.write(1) � � while True:� body()� (AXI4/Avalon) slave interface (AXI4/Avalon) master interface BRAMからDRAMへDMA転送 DRAMからBRAMへDMA転送
  13. 13. testbench.v n  このファイルの内容が自動的にテストベンチ本体 (pycoram_userlogic_v1_00_a/test/test_pycoram_userlogic.v) に追記される l  iochannel (Slaveインターフェース)にアクセスする task文が自動的に生成されるのでそれを利用してアクセス 2015-03-19 Shinya T-Y, NAIST 13 reg [31:0] read_val;� � initial begin� #1000;� wait(sim_resetn == 1);� nclk();� iochannel_write_ctrl_thread_coramiochannel_0(0, 0); // src� iochannel_write_ctrl_thread_coramiochannel_0(1024, 0); // dst� iochannel_write_ctrl_thread_coramiochannel_0(128, 0); // size (byte)� nclk();� iochannel_read_ctrl_thread_coramiochannel_0(read_val, 0);� nclk();� #1000;� � nclk();� iochannel_write_ctrl_thread_coramiochannel_0(0, 0); // src� iochannel_write_ctrl_thread_coramiochannel_0(8192, 0); // dst� iochannel_write_ctrl_thread_coramiochannel_0(8192, 0); // size (byte)� nclk();� iochannel_read_ctrl_thread_coramiochannel_0(read_val, 0);� nclk();� #1000;� $finish;� end�
  14. 14. シミュレーションで動作確認する n  Icarus Verilogで実行しGTKWaveで波形を確認 2015-03-19 Shinya T-Y, NAIST 14 make sim� make view�
  15. 15. GTKWaveで波形を確認する 2015-03-19 Shinya T-Y, NAIST 15 n  RVALIDのフェーズの後にWVALIDのフェーズが来る n  アドレス (ARADDR, AWADDR) と データ (RDATA, WDATA) を見ると 正しく転送されているのがわかる
  16. 16. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 16
  17. 17. Vivadoを起動する n  作業用ディレクトリを作成 (work/vivado_zynq_pycoram) n  “ip”というディレクトリを作成 n  その中にPyCoRAM IPコアをコピー n  設定ファイルを読み込みVivadoを起動 2015-03-19 Shinya T-Y, NAIST 17 mkdir -p ~/work/vivido_zynq_pycoram� cd ~/work/vivido_zynq_pycoram� mkdir ip� cp -r ~/work/PyCoRAM/sample/test/� memcpy/pycoram_userlogic_v1_00_a ip/� 一行に続けて入力 source /opt/Xilinx/Vivado/2014.4/settings64.sh� vivado &�
  18. 18. Open Example Project 2015-03-19 Shinya T-Y, NAIST 18
  19. 19. Next 2015-03-19 Shinya T-Y, NAIST 19
  20. 20. Project nameを”zed”に 2015-03-19 Shinya T-Y, NAIST 20
  21. 21. Base Zynq Designを選択 2015-03-19 Shinya T-Y, NAIST 21
  22. 22. ZedBoardを選択 2015-03-19 Shinya T-Y, NAIST 22
  23. 23. Finish 2015-03-19 Shinya T-Y, NAIST 23
  24. 24. ZedBoardベースシステム完成 2015-03-19 Shinya T-Y, NAIST 24
  25. 25. IP Settingsを変更 2015-03-19 Shinya T-Y, NAIST 25
  26. 26. Add Repository 2015-03-19 Shinya T-Y, NAIST 26
  27. 27. 先ほど作成した”ip”ディレクトリを選択 2015-03-19 Shinya T-Y, NAIST 27
  28. 28. PyCoRAM IPコアが認識された 2015-03-19 Shinya T-Y, NAIST 28
  29. 29. Add IPでPyCoRAM IPコアを追加する 2015-03-19 Shinya T-Y, NAIST 29
  30. 30. pycoram_userlogic_v1_0を選択 2015-03-19 Shinya T-Y, NAIST 30
  31. 31. PyCoRAM IPコアが追加された ZynqをダブルクリックしてRe-customize IP 2015-03-19 Shinya T-Y, NAIST 31
  32. 32. 32ビット幅のHP0 Interfaceを追加 2015-03-19 Shinya T-Y, NAIST 32
  33. 33. Run Connection Automationを実行 2015-03-19 Shinya T-Y, NAIST 33
  34. 34. S_AXI_HP0とcorammemory_0_AXIを接続 2015-03-19 Shinya T-Y, NAIST 34
  35. 35. GP0とcoramiochannel_0_AXIを接続 2015-03-19 Shinya T-Y, NAIST 35
  36. 36. クロック・リセットを接続(繋ぐ前) 2015-03-19 Shinya T-Y, NAIST 36
  37. 37. リセットを接続 2015-03-19 Shinya T-Y, NAIST 37
  38. 38. クロックを接続 2015-03-19 Shinya T-Y, NAIST 38
  39. 39. アドレスをチェック(変更しない) 2015-03-19 Shinya T-Y, NAIST 39
  40. 40. Generate Bitstreamで合成 2015-03-19 Shinya T-Y, NAIST 40
  41. 41. 聞かれたらYes 2015-03-19 Shinya T-Y, NAIST 41
  42. 42. 合成が完了したらキャンセル 2015-03-19 Shinya T-Y, NAIST 42
  43. 43. File→Export→Export Hardware 2015-03-19 Shinya T-Y, NAIST 43
  44. 44. File→Launch SDK 2015-03-19 Shinya T-Y, NAIST 44
  45. 45. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 45
  46. 46. コマンドラインに戻ってU-Bootの作成 n  workへ移動しコンパイルの準備 n  U-Bootのダウンロード n  xilinx-v2014.4をチェックアウト 2015-03-19 Shinya T-Y, NAIST 46 cd ~/work� export CROSS_COMPILE=arm-xilinx-linux-gnueabi-� export ARCH=arm� git clone git://git.xilinx.com/u-boot-xlnx.git; cd u-boot-xlnx� git checkout -b xilinx-v2014.4 xilinx-v2014.4�
  47. 47. SDカードからブートするように編集 n  “include/configs/zynq-common.h” (-が削除,+が追加) 2015-03-19 Shinya T-Y, NAIST 47 emacs include/configs/zynq-common.h� diff --git a/include/configs/zynq-common.h b/include/configs/zynq-common.h� index db74f14..b3f821f 100644� --- a/include/configs/zynq-common.h� +++ b/include/configs/zynq-common.h� @@ -239,11 +239,11 @@� #define CONFIG_EXTRA_ENV_SETTINGS � "ethaddr=00:0a:35:00:01:220" a� "kernel_image=uImage0" � - "kernel_load_address=0x20800000" � + "kernel_load_address=0x30000000" � "ramdisk_image=uramdisk.image.gz0" � "ramdisk_load_address=0x40000000" � "devicetree_image=devicetree.dtb0" � - "devicetree_load_address=0x20000000" � + "devicetree_load_address=0x2A000000" � "bitstream_image=system.bit.bin0" � "boot_image=BOOT.bin0" � "loadbit_addr=0x1000000" � @@ -289,8 +289,7 @@� "echo Copying Linux from SD to RAM... && " � "fatload mmc 0 ${kernel_load_address} ${kernel_image} && " � "fatload mmc 0 ${devicetree_load_address} ${devicetree_image} && " � - "fatload mmc 0 ${ramdisk_load_address} ${ramdisk_image} && " � - "bootm ${kernel_load_address} ${ramdisk_load_address} ${devicetree_load_address}; " � + "bootm ${kernel_load_address} - ${devicetree_load_address}; " � "fi0" � “usbboot=if usb start; then ” �
  48. 48. U-Bootをビルド n  デフォルトの設定をロードしてからコンパイル n  出来上がったu-bootをVivadoのディレクトリにコピー n  u-boot.elf完成 2015-03-19 Shinya T-Y, NAIST 48 make zynq_zed_config� make� cp u-boot ~/work/vivado_zynq_pycoram/u-boot.elf�
  49. 49. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 49
  50. 50. SDKでFile→New→Project 2015-03-19 Shinya T-Y, NAIST 50
  51. 51. Application Projectを選択しNext 2015-03-19 Shinya T-Y, NAIST 51
  52. 52. Project nameをfsblとしてNext 2015-03-19 Shinya T-Y, NAIST 52
  53. 53. Zynq FSBLを選択しFinish 2015-03-19 Shinya T-Y, NAIST 53
  54. 54. fsblを右クリックしCreate Boot Imageを選択 Addをクリック 2015-03-19 Shinya T-Y, NAIST 54
  55. 55. Browse 2015-03-19 Shinya T-Y, NAIST 55
  56. 56. 先ほど作成したu-boot.elfを選択 2015-03-19 Shinya T-Y, NAIST 56
  57. 57. OK 2015-03-19 Shinya T-Y, NAIST 57
  58. 58. Create Image 2015-03-19 Shinya T-Y, NAIST 58
  59. 59. 完成したBOOT.binをコピー n  bootimage/BOOT.binをBOOT.BINとしてコピー n  VivadoとSDKを閉じる 2015-03-19 Shinya T-Y, NAIST 59 cp ~/work/vivado_zynq_pycoram/zed.sdk/fsbl/� bootimage/BOOT.bin ~/work/BOOT.BIN� 1行で続けて
  60. 60. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 60
  61. 61. uImage (カーネルイメージ) のダウンロード n  Gitでダウンロードしxcomm_zynqをチェックアウト n  Zynq用設定を適用しmenuを開く n  “Device Drivers”→“Userspace I/O drivers”を選択し すべてに<*>がついていることを確認する(図参照) n  “less .config”として以下の設定があることを確認する 2015-03-19 Shinya T-Y, NAIST 61 cd ~/work� git clone https://github.com/analogdevicesinc/linux.git ; cd linux � git checkout xcomm_zynq� make zynq_xcomm_adv7511_defconfig� make menuconfig� CONFIG_UIO=y� CONFIG_UIO_PDRV=y� CONFIG_UIO_PDRV_GENIRQ=y�
  62. 62. NFSの設定(必要があれば設定) n  研究室などでNFSでファイルシステムを共有する場合に 要設定(単独で利用する場合には不要ためスキップ) n  NFSを利用するにはカーネルでNFSをONにする n  “File systems”→”Network file systems”を<*>にする n  NFS関連のオプションを<*>で選択する(図参照) n  “less .config”として以下の設定があることを確認する (次ページ参照) 2015-03-19 Shinya T-Y, NAIST 62
  63. 63. 2015-03-19 Shinya T-Y, NAIST 63 CONFIG_NETWORK_FILESYSTEMS=y� CONFIG_NFS_FS=y� CONFIG_NFS_V2=y� CONFIG_NFS_V3=y� CONFIG_NFS_V3_ACL=y� CONFIG_NFS_V4=y� CONFIG_NFS_SWAP=y� CONFIG_NFS_V4_1=y� CONFIG_NFS_V4_2=y� CONFIG_PNFS_FILE_LAYOUT=y� CONFIG_NFS_V4_1_IMPLEMENTATION_ID_DOMAIN="kernel.org"� CONFIG_NFS_V4_1_MIGRATION=y� # CONFIG_ROOT_NFS is not set� CONFIG_NFS_USE_LEGACY_DNS=y� # CONFIG_NFSD is not set� CONFIG_GRACE_PERIOD=y� CONFIG_LOCKD=y� CONFIG_LOCKD_V4=y� CONFIG_NFS_ACL_SUPPORT=y� CONFIG_NFS_COMMON=y�
  64. 64. menuconfigの設定: UIO (1) 2015-03-19 Shinya T-Y, NAIST 64
  65. 65. menuconfigの設定: UIO (2) 2015-03-19 Shinya T-Y, NAIST 65
  66. 66. menuconfigの設定: UIO (3) 2015-03-19 Shinya T-Y, NAIST 66
  67. 67. menuconfigの設定 : NFS (1) 2015-03-19 Shinya T-Y, NAIST 67
  68. 68. menuconfigの設定 : NFS (2) 2015-03-19 Shinya T-Y, NAIST 68
  69. 69. menuconfigの設定 : NFS (3) 2015-03-19 Shinya T-Y, NAIST 69
  70. 70. uImage (カーネルイメージ) のコンパイル n  PATHの設定 n  コンパイル n  完成したuImageはlinux/arch/arm/bootにあるのでコピー 2015-03-19 Shinya T-Y, NAIST 70 export PATH=/home/yourname/work/u-boot-xlnx/tools:$PATH� make uImage LOADADDR=0x00008000� cp ~/work/linux/arch/arm/boot/uImage ~/work�
  71. 71. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 71
  72. 72. Device Tree設定ファイルの編集 n  zynq-zed.dtsi を編集する (-が削除,+が追加) n  “mem=256M” を追加しLinuxに割り当てるメモリ量を256MBに制限 n  “dmem-io”で /dev/uioX を追加している l  usermemoryでDRAM後半256MBを /dev/uio0 に割り当て l  pycoram0は /dev/uio1 •  アドレス・サイズ値はVivadoでのAddress Editorと同じにする 2015-03-19 Shinya T-Y, NAIST 72 emacs ~/work/linux/arch/arm/boot/dts/zynq-zed.dtsi� chosen {� - bootargs = "console=ttyPS0,115200 root=/dev/mmcblk0p2 rw earlyprintk rootfstype=ext4 rootwait";� + bootargs = "console=ttyPS0,115200 mem=256M root=/dev/mmcblk0p2 rw earlyprintk rootfstype=ext4 rootwait";� linux,stdout-path = "/amba@0/uart@E0001000";� };� � + usermemory {� + compatible = "dmem-uio";� + reg = < 0x10000000 0x10000000 >; // (address, size)� + };� +� + pycoram0 {� + compatible = "dmem-uio";� + reg = < 0x43c00000 0x10000 >; // (address, size)� + };� +�
  73. 73. Device Tree設定ファイルの追加 n  zynq-zed-pycoram.dts を作成する(ほぼ空) 2015-03-19 Shinya T-Y, NAIST 73 touch ~/work/linux/arch/arm/boot/dts/zynq-zed-pycoram.dts� emacs ~/work/linux/arch/arm/boot/dts/zynq-zed-pycoram.dts� /dts-v1/;� � /include/ "zynq-zed.dtsi”�
  74. 74. Device Treeのコンパイル n  Linuxディレクトリの中でmakeする n  linux/arch/arm/boot/dts/zynq-zed-pycoram.dtb をコピー 2015-03-19 Shinya T-Y, NAIST 74 cd ~/work/linux� make zynq-zed-pycoram.dtb� cp ~/work/linux/arch/arm/boot/dtb/zynq-zed-pycoram.dtb� ~/work/devicetree.dtb� 1行で続けて
  75. 75. uEnv.txtの作成 n  uEnv.txtに以下の内容を書き込む 2015-03-19 Shinya T-Y, NAIST 75 emacs ~/work/uEnv.txt� fdt_high=0x10000000� initrd_high=0x10000000�
  76. 76. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 76
  77. 77. rootfs構築のための環境設定 n  各種ツールをインストールし環境変数を設定 n  $targetdirの中に構築開始 2015-03-19 Shinya T-Y, NAIST 77 cd ~/work� sudo apt-get install qemu-user-static debootstrap binfmt-support� export targetdir=rootfs� export distro=wheezy� mkdir $targetdir� sudo debootstrap --arch=armhf --foreign $distro $targetdir� sudo cp /usr/bin/qemu-arm-static $targetdir/usr/bin� sudo cp /etc/resolv.conf $targetdir/etc� sudo chroot $targetdir�
  78. 78. QEMUを使ってrootfs構築 (1) n  下記コマンドを順次入力 2015-03-19 Shinya T-Y, NAIST 78 distro=wheezy � export LANG=C� /debootstrap/debootstrap --second-stage� cat <<EOT > /etc/apt/sources.list� deb http://ftp.jp.debian.org/debian $distro main contrib non-free� deb-src http://ftp.jp.debian.org/debian $distro main contrib non-free� deb http://ftp.debian.org/debian $distro-updates main contrib non-free� deb-src http://ftp.debian.org/debian $distro-updates main contrib non-free� deb http://security.debian.org/debian-security $distro/updates main contrib non-free� deb-src http://security.debian.org/debian-security $distro/updates main contrib non-free� EOT� cat << EOT > /etc/apt/apt.conf.d/71-no-recommends� APT::Install-Recommends "0";� APT::Install-Suggests "0";� EOT�
  79. 79. QEMUを使ってrootfs構築 (2) n  下記コマンドを順次入力: passwdでrootパスワード設定 n  IPアドレス等は環境に応じて設定する 2015-03-19 Shinya T-Y, NAIST 79 apt-get update� apt-get install locales dialog � dpkg-reconfigure locales� apt-get install openssh-server ntpdate resolvconf sudo less hwinfo ntp tcsh zsh� passwd� echo <<EOT >> /etc/network/interfaces� auto eth0� iface eth0 inet static� address 192.168.0.100� netmask 255.255.255.0� gateway 192.168.0.1� dns-nameservers 192.168.0.1� EOT�
  80. 80. QEMUを使ってrootfs構築 (3) n  resolv.conf も同様 n  /etc/ssh/sshd_config の設定を確認: n  l  “PasswordAuthentication yes” 2015-03-19 Shinya T-Y, NAIST 80 echo <<EOT >> /etc/resolv.conf� nameserver 192.168.0.1� EOT� vi /etc/ssh/sshd_config�
  81. 81. QEMUを使ってrootfs構築 (4) n  いろいろインストール n  必要あればNISとNFSをインストール(しなくて良い) n  終了し不要なファイルを削除 2015-03-19 Shinya T-Y, NAIST 81 echo debian-zynq > /etc/hostname� echo T0:2345:respawn:/sbin/getty -L ttyS0 115200 vt1000 >> /etc/inittab� apt-get install screen bash-completion emacs time� apt-get install gcc g++ gcc-4.7 g++-4.7� apt-get install python python-pip python3 python3-pip� apt-get install nis nfs-common� exit� sudo rm -f $targetdir/usr/bin/qemu-arm-static�
  82. 82. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 82
  83. 83. SDカードをフォーマットする n  16GB以上あると良い n  GpartedでSDカードのパーティションを編集 l  インストールして実行 n  先頭から以下の様な構成にする l  空き領域 (4MB) l  BOOT (64MB, FAT32, bootableフラグ追加) l  rootfs (残りすべて, ext4) 2015-03-19 Shinya T-Y, NAIST 83 sudo apt-get install gparted –y� sudo gparted &�
  84. 84. SDカードに書き込む n  /media/yourname/BOOT/に4つのファイルをコピー n  /media/yourname/rootfs/に~/work/rootfs/の内容をコピー n  システム完成! l  ジャンパーピンの設定を確認 l  イーサネットケーブルを差し込みネットワークに接続 l  SDカードをZedBoardに差し込んで起動しましょう 2015-03-19 Shinya T-Y, NAIST 84 cp ~/work/BOOT.BIN /media/yourname/BOOT/� cp ~/work/devicetree.dtb /media/yourname/BOOT/� cp ~/work/uEnv.txt /media/yourname/BOOT/� cp ~/work/uImage /media/yourname/BOOT/� sudo cp -a ~/work/rootfs/* /media/yourname/rootfs/�
  85. 85. ジャンパーピン 2015-03-19 Shinya T-Y, NAIST 85
  86. 86. 開発手順 n  開発環境の準備 n  PyCoRAM/Pyverilogのダウンロード n  IPコア作成 n  Vivadoで合成 n  U-Bootのコンパイル n  SDKでブートイメージ (BOOT.BIN) の作成 n  Linuxカーネルイメージの作成 n  Device Treeの作成 n  Debian ルートファイルシステム (rootfs) の作成 n  SDカードへの書き込み n  Zynq+Debian上でプログラム実行 2015-03-19 Shinya T-Y, NAIST 86
  87. 87. ssh経由でログインする n  IPアドレスは先ほど設定したもの n  ID: root, パスワード: passwdで設定したもの n  こんな感じでログインできるはず 2015-03-19 Shinya T-Y, NAIST 87 ssh root@192.168.0.100�
  88. 88. memcpyプログラム (1) n  memcpy.c を作成する n  内容(次ページに続く) 2015-03-19 Shinya T-Y, NAIST 88 #include <stdio.h>� #include <stdlib.h>� #include <unistd.h>� #include <assert.h>� #include <sys/mman.h>� #include <fcntl.h>� � #define UIO_MEM "/dev/uio0"� #define UIO_PYCORAM "/dev/uio1"� � #define UMEM_SIZE (0x10000000)� #define UMEM_ADDR (0x10000000)� #define MAP_SIZE (0x00001000)� � void cache_clean(char* addr, int size)� {� __clear_cache(addr, addr + size);� }� � void usage()� {� printf("usage: pycoram_memcpy -s <size> -v <value> -cn");� }� touch memcpy.c�
  89. 89. memcpyプログラム (2) n  次のページに続く・・・ 2015-03-19 Shinya T-Y, NAIST 89 int main(int argc, char *argv[])� {� int c;� int value = 0;� int check = 0;� unsigned int size = 1024;� while ((c = getopt(argc, argv, "s:v:ch")) != -1) {� switch(c) {� case 's':� size = atoi(optarg);� break;� case 'v':� value = atoi(optarg);� break;� case 'c':� check = 1;� break;� case 'h':� usage();� return 0;� default:� printf("invalid option: %cn", c);� usage();� return -1;� }� }�
  90. 90. memcpyプログラム (3) n  次のページに続く・・・ 2015-03-19 Shinya T-Y, NAIST 90 int fd_mem = open(UIO_MEM, O_RDWR);� if(fd_mem < 1){� perror(argv[0]);� printf("Invalid UIO device file: '%s'n", UIO_MEM);� return -1;� }� volatile unsigned int *usermemory = (volatile unsigned int*) mmap(NULL, UMEM_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd_mem, 0);� � int fd_pycoram = open(UIO_PYCORAM, O_RDWR);� if(fd_pycoram < 1){� perror(argv[0]);� printf("Invalid UIO device file: '%s'n", UIO_PYCORAM);� return -1;� }� volatile unsigned int *pycoram = (volatile unsigned int*) mmap(NULL, MAP_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd_pycoram, 0);� � volatile int *a = (volatile int*) &usermemory[0];� volatile int *b = (volatile int*) &usermemory[size];�
  91. 91. memcpyプログラム (4) n  次のページに続く・・・ 2015-03-19 Shinya T-Y, NAIST 91 // initialization of data� int i;� � if(check) goto verify;� � for(i=0; i<size * 2; i++){� //printf("write %10dn", i);� a[i] = i + value;� }� � cache_clean((char*)usermemory, size * sizeof(int) * 2);� msync((void*)usermemory, UMEM_SIZE, MS_SYNC);� � int src = UMEM_ADDR;� int dst = UMEM_ADDR + size * sizeof(int);� � printf("memcpy from 'a' to 'b'n");� printf("src = %08xn", src);� printf("dst = %08xn", dst);� printf("size = %8dn", size);� � *pycoram = (volatile unsigned int) src;� printf(".");� *pycoram = (volatile unsigned int) dst;� printf(".");� *pycoram = (volatile unsigned int) size * sizeof(int);� printf(".n");� volatile int recv = *pycoram;�
  92. 92. memcpyプログラム (5) 2015-03-19 Shinya T-Y, NAIST 92 verify: if(check){ printf("check onlyn"); } cache_clean((char*)usermemory, size * sizeof(int) * 2); msync((void*)usermemory, UMEM_SIZE, MS_INVALIDATE); int mismatch = 0; for(i=0; i<size; i++){ //printf("read %10dn", b[i]); if(a[i] != b[i]){ mismatch = 1; printf("%10d %10dn", a[i], b[i]); } if(i==size-1){ //printf("read %10dn", b[i]); } } if(mismatch){ printf("NGn"); }else{ printf("OKn"); } munmap((void*) usermemory, UMEM_SIZE); munmap((void*) pycoram, MAP_SIZE); return 0; }
  93. 93. memcpyプログラムについて n  ARMで初期値を設定し, PyCoRAM IPコアで違う領域へコピーしてもらい, 最後に正しくコピーされているかどうかを確認する n  なぜ /dev/uio0 をmmapしているのか? l  DRAM前半256MBはLinux管理の領域のためPL側はデータが存在 する物理アドレスを知ることができない l  (物理アドレスがわかったとしても) 論理空間で連続していても物理空間で連続とは限らないため PL側での大規模データの取り扱いが面倒になる l  DRAM後半256MBをLinux非管理領域とし/dev/uio0にファイルと してマップ,PL側と連続256MBの領域を共有 l  mmapがデータをキャッシュする可能性があるのでmsyncで吐き 出している(もしかしてなくても良い) l  L1/L2キャッシュにDirtyなデータが残っている可能性があるので gcc拡張の__clear_cache(begin, end)でフラッシュ 2015-03-19 Shinya T-Y, NAIST 93
  94. 94. memcpyプログラムをコンパイル&実行 n  コンパイルする n  実行する n  このような実行結果が得られればOK l  どうでしたか? 2015-03-19 Shinya T-Y, NAIST 94 gcc -O2 memcpy.c� ./a.out -s 4096�
  95. 95. 補足:もしHDMIを使いたい場合には n  Analog Devicesが配布しているリファレンスデザインを 利用するのが良い l  ADI Reference Designs HDL User Guide •  http://wiki.analog.com/resources/fpga/docs/hdl •  https://github.com/analogdevicesinc/hdl l  Vivado 2014.2を対象としておりいくつかのファイルが要修正 l  IPコアをVivado上のtclで自前でビルドする必要があり面倒 l  ZC706等のボードのリファレンスデザインも同梱 n  上記リファレンスデザインでも PyCoRAM IPコアが動作することは確認済み 2015-03-19 Shinya T-Y, NAIST 95
  96. 96. 補足:その他 n  /usr/bin/sudo のパーミッションがおかしいので修正する n  /etc/hosts にホスト名を書く n  sudoersの設定にはvisudoを使う n  root以外が /dev/uio* を使う場合には パーミッションを変更する 2015-03-19 Shinya T-Y, NAIST 96 chmod 6755 /usr/bin/sudo� 127.0.0.1 localhost yourhostname� chmod 777 /dev/uio*�
  97. 97. 参考にしたウェブサイト n  Zynq + Vivado HLS入門 l  http://www.slideshare.net/narusugimoto/zynq-vivado-hls?related=1 n  Zynq + Synthesijer入門 l  http://www.slideshare.net/miyox/synthesijer-zynq-qs20150316 n  ZedBoard用のUbuntu Linuxをビルド: FPGAの部屋 l  http://marsee101.blog19.fc2.com/blog-entry-2813.html n  Yet Another Guide to Running Linaro Ubuntu Linux Desktop on Xilinx Zynq on the ZedBoard l  https://fpgacpu.wordpress.com/2013/05/24/yet-another-guide-to- running-linaro-ubuntu-desktop-on-xilinx-zynq-on-the-zedboard/ n  Building a pure Debian armhf rootfs l  https://blog.night-shade.org.uk/2013/12/building-a-pure-debian- armhf-rootfs/ n  ADI Reference Designs HDL User Guide l  http://wiki.analog.com/resources/fpga/docs/hdl 2015-03-19 Shinya T-Y, NAIST 97

×