Vivado HLS

Vivado HLSのExampleを試してみる1(axi_lite の生成)
今回は、Vivado HLSを試しにやってみたい。試してみるのは、Vivado HLSのExample Project だ。
axi_lite を試した。プロジェクトを生成するまで。
Vivado HLSのExampleを試してみる2(シミュレーションと合成)
C Simulation、 C Synthesisを行い、合成レポートを確認した。
Vivado HLSのExampleを試してみる3(インターフェイス)
Interface について調べてみた。axi_lite プロジェクトに使用されている ap_hs, ap_vld, ap_none インターフェースについて調べた。
Vivado HLSのExampleを試してみる4(C/RTL Cosimulation)
axi_liteプロジェクトで、C/RTL Cosimulationを行った。
Vivado HLSのExampleを試してみる5(IPにした)
axi_liteプロジェクトをIP化した。

Vivado HLSのAXI Master Exampleを試す1
今回は、AXI Master の Example を試した。論理合成して、結果を確認した。
Vivado HLSのAXI Master Exampleを試す2
前回に引き続き、AXI Master の Example を試した。C/RTL Cosimulation、IP化

Vivado HLSで作ったaxi_lite IPをテストした
Vivado HLSのExample として試した axi_lite IP をテストしてみた。IPを論理合成、インプリメントを行い成功した。

Vivado HLSで作ったaxi_master IPをテストした1(論理合成、インプリメント)
Vivado HLSのExample として試した axi_master IP をテストしてみた。論理合成は通ったが、インプリメントでエラーが発生した。

ラプラシアン・フィルタのCソフトをVivado HLSで

ソ フトウエアのプロファイリング4(ハードウェアと同じ方式)”のラプラシアン・フィルタのCソフトウェアをVivado HLSでコンパイルしてHDLコードの落として使ってみたい。そのため、Cプログラムを修正してVivado HLSでプロジェクトを作製してコンパイルしてみた。
ソフトウェアで使っていたCプログラムをそのまま、Vivado HLSで変換したので、変換できず、エラーでコンパイルできなかった。
Vivado HLSでラプラシアン・フィルタ式のみをaxi lite slaveモジュールにする1
今回は、3x3のラプラシアン・フィルタの式のみを、以前Vivado HLSのサンプルしてやってみた axi lite を元に変更してみようと思う。
C Synthesis まで行った。
Vivado HLSでラプラシアン・フィルタ式のみをaxi lite slaveモジュールにする2
Verilog HDLのCo-Simulation し、カスタムIPとして出力した。使用 したCソフトウェアの laplacian_filter.c を貼っておく。
Vivado HLSでラプラシアン・フィルタ式のみをaxi lite slaveモジュールにする3
記事が前後してしまったが、Vivado HLSで生成されたVerilog HDLコードをシミュレーションしてみようと思う。
生成されたVerilogはC言語のテストベンチでCo-Simulation してみたがタイミングチャートにして表示する方法がわからなかった。そこで、ISEのプロジェクトを作って、ISimでシミュレーションしてみた。

Vivado HLSでラプラシアン・フィルタ関数をaxi masterモジュールにする1
ラプラシアン・フィルタ関数自体をVivado HLSで、AXI4 Master を使用したIPとして生成することにした。
Vivado HLSで合成はできたが、画像のフレームバッファが固定値なので、使いものにならない。
Vivado HLSでラプラシアン・フィルタ関数をaxi masterモジュールにする2
前回、Vivado HLS の Export RTL で EDK用の pcore を作ってみたが、カメラ画像フレーム・バッファ読み込み用アドレスとラプラシアン・フィルタの結果を書き出すフレーム・バッファのアドレスは、parameter 指定の固定アドレスだったので、AXI4 Lite Slave でAXI4 Master のRead/Writeするアドレスを渡す仕様に変更した。Vivado HLSのCソースコードを貼った。

Vivado HLSのaxi_stream_no_side_channel_dataを試す1
先週の金曜日の Zynq-7000 All Programmable SoC Seminar 2013 でAXI Master より、AXI Streamで実装したほうが、Vivado HLSで正常にコンパイル、シミュレーション出来そうだということを聞いてきた。早速、Example をやってみようと思った。
最初にやるのは、Vivado HLSのaxi_stream_no_side_channel_data というExampleだ。
Vivado HLSのaxi_stream_side_channel_dataを試す
今回は、axi_stream_side_channel_dataを試すことにする。

Vivado HLS 2013.3でラプラシアン・フィルタ関数をaxi masterモジュールにする
Xilinxのサイトに、Vivado 2013.3 と ISE14.7 が出ているということをツイッターで教えてもらったので、早速、Vivado 2013.3 をインストールした。そして、再度、Vivado HLSでラプラシアン・フィルタ関数をaxi masterモジュールにしてみた。
ラプラシアン・フィルタのCソースを少し変更したので、貼っておく。キャストが違っていて、 warnningがでていたので、その点を修正した。

Vivado HLSの現状について

今日のfpgaxで、Vivado HLSについて説明不足があったので、ブログで現状を解説します。

Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする
一昨日、Vivado 2013.4 が出たので、再度、Vivado HLS でC言語からラプラシアン・フィルタのAXI4 Master IPを生成した。
2013.3から2013.4の差分を見ると、1つの Verilog HDL ファイルが増えた。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする2
前回、IPをエクスポートできたので、”AXI4 Master アクセスのラプラシアン・フィルタ IP9(できた。完成)”のXPSプロジェクトにVivado HLS生成ラプラシアン・フィルタAXI4 Master IPコアが入っているので、入れ替えた。インプリメントしてやってみたが、うまく行かなかった。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする3
S様にVivado HLSについてお尋ねしたら、私のラプラシアン・フィルタを評価していただけるということなので、お願いしたら、デバックして頂いた。その知見を元に、私なりに今までのラ プラシアン・フィルタのコードを見なおしてみたい。
もう一度、ラプラシアン・フィルタのCコードからのHDL合成にチャレンジすることにした。
最初に、Vivado HLS 2013.4でCシミュレーションすると、何でおかしいのか?よく分からないので、Cシミュレーションは、Visual Studio 2012 でやることにした。
S様のアドバイスを元に修正したのだが、いろいろと間違っていた。修正して、Visual Studio 2012でデバックし、動かすことができた。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする4
前回は、Visual Studio 2012 でVivado HLS 2013.4 に使うためのCソースをシミュレーションしてみた。うまく行ったので、今回は、Vivado HLS 2013.4 に持ってきてCシミュレーションやCからHDLへの合成、IP化などを行った。
初めて C Simulation で成功した
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする5(単体シミュレーション)
前回、Vivado HLS 2013.4 でラプラシアンフィルタのAXI4 Master IPを生成できたので、今度は単体シミュレーションを行った。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする6(実機でテスト)
インプリメントして、実機でテストを行ったところ、表示はされたのだが、画像は全体的に強調さ れていて、余計な線が入っている。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする7(ソース公開)
前回までのソースを公開した。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする8(Directive)
Vivado HLS 2013.4 でラプラシアンフィルタのCソースコードをVerilog HDLで書かれたIPとして高位合成をして、できたIPを実機でテストしてみたところ、結果はちょっとおかしいが、無事に動作した。今回は、実行時間が約 100msec 程度と遅いので、もう少し早くしてみようと思う。そのためには、Directiveを追加する必要がある。
なかなかうまく行かなかった。
Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする9(Directive2)
前回は、UNROLL Directive を入れてたが効果は得られなかった。あれからPIPELINE Directive を試してみたが、大きいループにPIPELINE Directive 属性を付加すると時間がかかりすぎる。小さいループにPIPELINE Directive をかけても他がPIPELINE化されていないので、効果なしという結果になるような気がする。

Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする1
Vivado HLS 2013.4 で作ってあったラプラシアンフィルタのIPをVivado HLS 2014.1 に移行することにした。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする2(実機でテスト)
今回は、Vivado HLS 2014.1で生成したラプラシアンフィルタIPを使用して、同様にラプラシアンフィルタ通過後の画像を比べてみた。
Vivado HLS 2013.4 で作製したラプラシアンフィルタとソフトウェアでのラプラシアンフィルタの結果に違いは見られなくなった。これは使えると思う。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする3(単体シミュレーション)
前回、Vivado HLS 2013.4 で作製したラプラシアンフィルタのIPの表示は、ソフトウェアで作製したラプラシアンフィルタと同一だったが、変換にかかる時間が遅かった。(注:時間計測ソ フトウェアが間違っていただけで、実際は遅くなかった)今回は、”Vivado HLS 2013.4でラプラシアン・フィルタ関数をaxi masterモジュールにする5(単体シミュレーション)”のプロジェクトで単体シミュレーションを行った。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする4(ChipScope Proでデバック)
シミュレーションでは、Vivado HLS 2013.4 で出力したラプラシアンフィルタIPと総違いは無かった。今回はChipScope Proで実際のAXIバスの波形を観察した。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする5(Cソースのフィルタ処理をパイプライン化)
twitter で tu1978 さんに、私のラプラシアンフィルタのCソースのフィルタ処理をパイプライン化して頂いたので、そのVivado HLS 2014.1合成結果と以前の合成結果を比べてみようと思う。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする6(パイプライン化ソースを実機テスト1)
前回は、twitter で tu1978 さんに頂いたフィルタ処理をパイプライン化したラプラシアンフィルタのCソースを合成した。今日は、XPS用のIPを生成して実機テストしてみた。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする7(パイプライン化ソースを実機テスト2)
前回、ISEでタイミング・エラーが発生したので、Vivado HLS 2014.1 に戻って、タイミング制約を変更することにした。
タイミング制約を変更してもダメだったので、動作周波数を変更することにした。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする8(パイプライン化ソースを実機テスト3)
前回、インプリメント時のタイミング制約のエラーが消えなかった。そこで、Vivado HLS 2014.1 のラプラシアンフィルタのIPの動作クロックを 100MHz か 90MHz にすることにした。計算上の限界は 94MHz だったが、XPSのClock Generator IP に 94MHz に動作クロックを設定したら、エラーになってしまったので、90MHz とすることにした。
Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする9(単体シミュレーション)
まずは、tu1978 さんに教えて頂いたラプラシアンフィルタ処理をパイプライン化したCソースをVivado HLS 2014.1 でIPにしたものを単体シミュレーションする。単体シミュレーションは、AXI4 Slaveメモリか、もしくはAXI4 Slave として動作するBFM(Bus Functional Model)を使用している。
Vivado HLS 2014.4 の勉強1(高位合成の理解)
Vivado HLSの教科書を参考にして、Vivado HLSの勉強をすることにした。簡単な例で勉強した。
Vivado HLS 2014.4 の高位合成テスト1(Vivado HLSで高位合成)
前回、引用した最初の関数 foo() を実際にVivado HLS 2014.4 で高位合成を行った。
Vivado HLS 2014.4 の高位合成テスト2(foo1のHDLコード)
前回は、”Vivado Design Suite ユーザー ガイド 高位合成 UG902 (v2014.1) 2014 年 4 月 2 日”の6ページのコード例を foo1 としてVivado HLS で高位合成を行った。
今回は高位合成の結果出力されたHDLを見てみよう。
Vivado HLS 2014.4 の高位合成テスト3(foo2 を Vivado HLS で高位合成)
今回は、”Vivado HLS 2014.4 の勉強1(高位合成の理解)”のもう1つのfoo() の高位合成をやってみる。今回のfoo() をfoo2 とする。foo2 は、入力の引数と出力の引数が配列になっているので、BlockRAM のインターフェースになっているはずだ。
Vivado HLS 2014.4 の高位合成テスト4(Vivado HLS で高位合成したfoo2 を シミュレーション)
高位合成された foo.v をシミュレーションしてみた。
Vivado HLS 2014.4 の高位合成テスト5(Vivado HLS で高位合成したfoo2 を 論理合成)
前回は、foo2 プロジェクトをシミュレーションしたので、今回は、論理合成を行った。
Vivado HLS 2014.4 の高位合成テスト6(ラプラシアンフィルタ1)
今回はラプラシアンフィルタをVivado HLS 2014.4 で高位合成してみた。
Vivado HLS で laplacian_filter プロジェクトを作製した。例によって、FPGAはZYBO に使用されている xc7z010clg400-1 とした。
Vivado HLS 2014.4 の高位合成テスト7(ラプラシアンフィルタ2、シミュレーション)
前回、ラプラシアンフィルタをVivado HLS 2014.4 で高位合成して、laplacian_filter.v と laplacian_filter.vhd のファイルを生成した。
今回は、その laplacian_filter.v を使用してシミュレーションを行った。
Vivado HLS 2014.4 の高位合成テスト8(ラプラシアンフィルタ3、論理合成)
前回はシミュレーションを行ったので、今回は、laplacian_filter.v を論理合成してみた。
Vivado HLS 2014.4 の高位合成テスト9(ラプラシアンフィルタ4、LATENCYディレクティブ)
今回は、LATENCYディレクティブを設定して、現在のLatency = 2 から、Latency = 1 への性能の改善を目指す。
Vivado HLS 2014.4 の高位合成テスト10(ラプラシアンフィルタ5、LATENCYディレクティブのシミュレーション)
前回は、laplacian_filter.cpp に LATENCY ディレクティブを追加して、Latencyを 2 から 1 に改善したが、Estimated は 12.46 ns となって規格を満足しなくなってしまった。
今回は、Latency = 1 で生成したHDLファイルをシミュレーションしてみた。
Vivado HLS 2014.4 の高位合成テスト11(ラプラシアンフィルタ6、PIPELINEディレクティブ)
今回は、ラプラシアンフィルタのCソースで、PIPELINEディレクティブを試してみること にした。
Vivado HLS 2014.4 の高位合成テスト12(ラプラシアンフィルタ7、PIPELINEディレクティブのシミュレーション)
前回は、ラプラシアンフィルタのCソースコードに、PIPELINEディレクティブを追加して 高位合成を行った。
今回は、合成されたVerilog HDL コードのシミュレーションを行った。
Vivado HLS 2014.4 の高位合成テスト13(ラプラシアンフィルタ8、Clock Period の変更1)
”Vivado HLS 2014.4 の高位合成テスト11(ラプラシアンフィルタ6、PIPELINEディレクティブ)”でラプラシアンフィルタをPIPELINEディレクティブを追加して高位合成したら、 latency = 2 だった。それでは、latency の値が変更される時はどんな時だろうか?
それは、Vivado HLSでは、Clock Period が変化した時ではないだろうか?
Clock Period が短くなって、つまり動作周波数が上がって、1クロックでやっていた演算の数が減っていくと latency は伸びていくだろう?
逆に、Clock Period が長くなって、つまり動作周波数が下がって、1クロックでやっていた演算の数が減ると latency は縮まるだろう?
Clock Period = 9 ns から 5 ns までやってみた。
Vivado HLS 2014.4 の高位合成テスト14(ラプラシアンフィルタ9、Clock Period の変更2)
前回は、Clock Period = 5 ns の場合までラプラシアンフィルタを高位合成したので、今回は次のClock Period = 4 ns の場合から、最後、動作周波数が高すぎてEstimated の値がタイミングを満たせなくなるまでやってみた。
Clock Period = 4 ns , 3 ns, 2 ns, 20 ns の場合を試した。3 ns まで行けた。
Vivado HLS 2014.4 の高位合成テスト15(ラプラシアンフィルタ10、Clock Period = 4 ns の場合のシミュレーション)
今回は、Clock Period = 4 ns の場合、つまり、Latency = 7 クロックの時に出力された Verilog HDLファイルをシミュレーションしてみようと思う。
Vivado HLS 2014.4 の高位合成テスト16(ラプラシアンフィルタ11、Clock Period = 4 ns の場合のインプリメント)
前回は、Vivado HLS 2014.4 でラプラシアンフィルタのCソースから高位合成したVerilog HDLをシミュレーションした。
今回は、そのラプラシアンフィルタの Verilog HDLファイルをVivado 2014.4でインプリメントしてみた。
Vivado HLS 2014.4 の高位合成テスト17(ラプラシアンフィルタ12、Clock Period = 2.5 ns の場合のインプリメント)
Clock Period = 2.5 ns で、ラプラシアンフィルタのCソースからVivado HLS 2014.4 で高位合成されたVerilog HDLファイルをVivado 2014.4でインプリメントして、400MHzつまり 2.5 ns の遅延で実際に動作するようにインプリメントできるかを確認する。
動くみたいですよ。ZYBOが400MHzでラプラシアンフィルタの演算をパイプライン処理できるとは思わなかった。
Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする1
”Vivado HLS 2014.1でラプラシアン・フィルタ関数をaxi masterモジュールにする1”で使用しているラプラシアンフィルタのCソースを使ってIP化してみた。
Vivado HLS 2014.4では、2014.1まで使っていたAXIバス用のディレクティブが変更になった。
Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする2
前回はC Synthesis アイコンで高位合成を行った。今回は、Export RTL アイコンで IP 化を行った。
Vivado HLS 2014.4 で生成した IP の example
”Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする2”で生成したラプラシアン・フィルタIPの example があったので、やってみた。

Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする3(IP Catalog にVivado HLSのIPを追加)

”Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする2”で、以前からやっているラプラシアンフィルタを Vivado HLS 2014.4 でIP化できた。途中、AXI4バスを生成するディレクティブが変更になっていて戸惑ったが、IP化することができたので、”ZYBO用の Linaro Ubuntu のPL部にカメラ・コントローラを搭載する11(Linuxで確認)”でできたZYBOでカメラ画像を表示するVivado プロジェクトを Vivado 2014.4 にアップデートして、今回作製したVivado HLS 2014.4 のラプラシアンフィルタIPを追加することにした。
Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする4(ブロックデザインにVivado HLSのIPを追加、インプリメント)
Vivado HLSで作製したラプラシアンフィルタIPを V_ZYBO_CAMDfLブロックデザイン上にインスタンスして論理合成、インプリメントを行った。
Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする5(BOOT.bin, devicetree.dtb の生成)
Vivado HLSで作製したラプラシアンフィルタIPを V_ZYBO_CAMDfLブロックデザイン上にインスタンスして論理合成、インプリメントを行った。今回は、SDKを立ちあげてBOOT.binを作製した。
Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする6(/sys, /devディレクトリ)
前回、Vivado HLS 2014.4 で作製したラプラシアンフィルタIPが入ったBOOT.bin とそのUIOの項目を追加したで devicetree.dtb を作製した。今回は、その BOOT.bin と devicetree.dtb を MicroSDカードの第1パーティション ZYBO_BOOT に入れて、ZYBOに挿入して電源をONし、起動するかどうか?を確かめてみた。

Vivado 2014.4のCドライバーファイル1

Vivado HLS は、C のドライバーファイルを生成してくれるので、これを使わない手は無い。ということで、”Vivado Design Suite ユーザー ガイド 高位合成 UG902 (v2014.3) 2014 年 10 月 1 日”(以下、高位合成ユーザーズガイドと呼ぶことにする)を読んで勉強することにした。
C のドライバーファイルの使い方を書いた。
Vivado 2014.4のCドライバーファイル2
前回は、Vivado HLS 2014.4 で生成されたドライバーを使う方法について検討し、初期化ルーチン XLap_filter_axim_Initialize() の動作について考察した。今回は、初期化の後の関数の使用方法について検討した。

ZYBO Linux (Ubuntu 14.04 LTS) 上でMakefile を作ってラプラシアンフィルタIPの制御ソフトをコンパイル
ZYBO のLinux 上でVivado HLSで生成された制御ソフト(Cドライバー・ソフトウェア)をコンパイルして動作させることにした。
ZYBO Linux (Ubuntu 14.04 LTS) 上でMakefile を作ってラプラシアンフィルタIPの制御ソフトをコンパイル2
前回、Vivado HLS 2014.4 で作製したラプラシアンフィルタIPのAXI4 Lite Slave ポートにアクセスしたが、バスエラーになってしまった。今回はその原因を探った。
画像が表示されたが、28秒かかってしまった。原因はVivado HLSのラプラシアンフィルタのCソースコードが間違っていたことだった。訂正記事へのリンクあり。
ZYBO Linux (Ubuntu 14.04 LTS) 上でMakefile を作ってラプラシアンフィルタIPの制御ソフトをコンパイル3
Vivado HLS 2014.1 でラプラシアンフィルタIPを作って、Vivado 2014.4 のプロジェクトを新規作成し、ブロック・デザインを構築していく過程で、ラプラシアンフィルタ IP のAXI4 Master バスは、カメラ・コントローラー IPとビットマップ・ディスプレイ・コントローラー IP のAXI4 Master が入っている AXI Interconnect に入っている。これをラプラシアンフィルタ IP 独自の AXI Interconnect にして、Zynq PS の AXI HP2 ポートに入れたらどうだろう?と考えた。
AXI4のバス帯域を考察してみた。

Vivado HLS 2014.1で生成したラプラシアンフィルタIPをZYBOのカメラ表示システム上で使用する1
Vivado HLS 2014.1 のプロジェクトを作製して、以前のVivado HLS 用のラプラシアンフィルタのCソースコードをプロジェクトに入れた。そして、高位合成して、IP化を行った。
バグフィックス版へのリンクあり
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをZYBOのカメラ表示システム上で使用する2
今回は、Vivado HLS 2014.1 で作製したラプラシアンフィルタ IP を ZYBO のVivado 2014.4 にプロジェクトのブロック・デザインの中に入れて論理合成、インプリメント、ビットストリームの生成後、BOOT.binの作製を行った。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをZYBOのカメラ表示システム上で使用する3
今回は、BOOT.binをMicro SDカードにコピーして、ZYBOに挿入して電源ONを行った。
制御用ソフトウェアを起動したら、ラプラシアンフィルタ処理のDONE待ち関数から1秒間帰ってこなかった。

Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション1(mem_sim_axi_slave IP の作製)
前回、Vivado HLS 2014.1 で作製したラプラシアンフィルタ IP が動作しなかったので、シミュレーションを行う。シミュレーションをしたのはZedBoardの時で、AXI4 Slave を持った汎用メモリモデル IP の mem_sim_axi_slave と設定レジスタを設定する AXI Lite Master IP の reg_set_axi_lite_master を使用する。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション2(reg_set_axi_lite_master IP の作製)
設定レジスタを設定する AXI Lite Master IP の reg_set_axi_lite_master を作製した。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション3( mem_sim_axi_slave IP の変更1)
”Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション1”で作った mem_sim_axi_slave IP のコードを少し修正することにした。
次に、Vivado HLS 2014.1 で作製したラプラシアンフィルタIP のシミュレーションをする予定なのだが、ラプラシアンフィルタIP のレジスタを設定する reg_set_axi_lite_master IP とメモリIP の mem_sim_axi_slave だけでは、メモリの値を書き換えるIP が存在しない。現在では、mem_sim_axi_slave の memory_8bit.v の中でメモリの初期値はオール 0 にクリアされているので、ラプラシアンフィルタIP でカメラデータを Read するために DMA しても、ラプラシアンフィルタ処理後のデータを Write するために DMA しても全て 0 のみとなる。これでは寂しいので、せめて、メモリの初期値を変更できるように、memory_8bit.v のメモリの初期値を変更できるようにした。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション4(mem_sim_axi_slave IP の変更2)
”Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション3”の mem_sim_axi_slave プロジェクトで IP を再IP化した。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション5(シミュレーション用プロジェクトの作製)
これで必要なIPが揃ったので、Vivado 2014.1 で作製したラプラシアンフィルタIP をシミュレーションするためのVivado 2014.4 のプロジェクトを作製した。
Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション6(シミュレーション)
前回はシミュレーション用プロジェクトを作成できたので、シミュレーションを行った。
Vivado HLS 2014.1 で高位合成したラプラシアンフィルタIPに設定することはできて、lap_fil_hls_sim_i -> lap_filter_axim_0 -> inst -> lap_filter_axim_LiteS_if_U の I_ap_start は 1 になったのだが、その後の cam_fb のAXIバスのReadが始まらない。

Vivado HLS 2014.4で生成したラプラシアンフィルタIPをシミュレーション1
”Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション6(シミュレーション)”で Vivado HLS 2014.1 で新たに作製したラプラシアンフィルタIP が動作しなったので、今度は、Vivado HLS 2014.4 で作製したラプラシアンフィルタIP をシミュレーションすることにした。
”Vivado HLS 2014.1で生成したラプラシアンフィルタIPをシミュレーション5(シミュレーション用プロジェクトの作製)”と同様にVivado 2014.4 のプロジェクトを作製し、シミュレーションを行った。
Vivado HLS 2014.4で生成したラプラシアンフィルタIPをシミュレーション2
前回、Vivado HLS 2014.4 でせいせいしたラプラシアンフィルタIP をVivado 2014.4 で、メモリIP やレジスタ値設定用IP などを追加して、ブロック・デザインを生成してシミュレーションを行った。
今回は、シミュレーションをもっと長く行って、ラプラシアンフィルタIP の実行時間が約27秒も掛かる原因を追求した。

Vivado HLS 2014.4で生成したラプラシアンフィルタIPをシミュレーション3(原因が分かった)
おるさんのおかげで、1ヶ月半くらいの間、悩んできた Vivado HLS 2014.4 で生成したラプラシアンフィルタIP の原因が分かりました。おるさんありがとうございました。
それは、古いバグありのラプラシアンフィルタのCソースコードを使用してしまったからです。正しいCソースコードはあったのですが、Vivado HLS プロジェクトの外に出してあって、バージョンの違うVivado HLS プロジェクトで使えるようになっていました。古いバグありCソースコードがプロジェクト内に残っていたので勘違いしてしまいました。反省しております。。。
新しいラプラシアンフィルタIP のCソースコードを貼っておきます。シミュレーションも行った。

ZYBO Linux (Ubuntu 14.04 LTS) 上でMakefile を作ってラプラシアンフィルタIPの制御ソフトをコンパイル4(うまく行った)
ラプラシアンフィルタIP のバグもフィックスできたので、もう一度、”Vivado HLS 2014.4でラプラシアン・フィルタ関数をaxi masterモジュールにする4(ブロックデザインにVivado HLSのIPを追加、インプリメント)”のラプラシアンフィルタ IP をバグ無しのものにすげ替えて、ラプラシアンフィルタのIPを更新し、もう一度、論理合成、インプリメント、ビットストリームの生成を行い、実機で確かめたところ問題なく 動作した。処理時間は約 95.4 ms だった。

Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化1(割り算を削除)
今回は、Vivado HLS のAnalysis 画面を見ながら、高速化を試みる。割り算の 代わりにカウンタで実装したが、あまり実行する頻度が高くないので、1%程度の改善となった。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化2(PIPELINEディレクティブ)
PIPELINEディレクティブを使用して高速化を試みた。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化3(PIPELINEディレクティブを実機テスト)
ZYBOでラプラシアンフィルタIP をテストして、実際にどのくらい速度が改善したか?を検証してみた。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化4(tu1978さんのCソースコード)
tu1978 さんの高速化ラプラシアンフィルタのIP化を行い、シミュレーションした。C ソースコードを貼り付けた。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化5(tu1978さんのCソースコードを実機で検証)
前回、IP化した tu1978 さんの高速化ラプラシアンフィルタIP を実機で検証してみることにした。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化6(動作周波数のチューンナップ)
tu1978さんが教えてくれたCソースコードを元に、Clock Periodを短くすることで、少しCソースコードをチューンナップしてみた。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化7(動作周波数のチューンナップを実機で検証)
PIPELINEディレクティブに依って高速化したラプラシアンフィルタIP がVivado HLS 2014.4 の見積値で 250MHz 動作が可能だった。これを実機で検証してみた。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化8(性能が最大になる設定を探る)
Vivado HLS 2014.4 のクロック周期制約を変えてみて、一番性能の出る辺りはどこか?を調査した。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化9(性能が最大になる設定を探る2)
PS の S_AXI_HP2_ACLK と S_AXI_HP2 につながる AXI Interconnect (axi_mem_intercon_1) の M00_ACLK を FCLK_CLK3 で駆動することにした。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化10(性能が最大になる設定を探る3)
間違っている記事なので参照しないこと。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化11(性能が最大になる設定を探る4)
今までのバグはHardware Platform Specification が新しくできた時に、プロジェクトをBSPごと作り直さなかったためだった。ハードウェアをエクスポートして、SDKを起動するときにFSBLがリビルドされ ていないのが原因だった。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化12(性能が最大になる設定を探る5)
Register Slice と Data FIFO のラプラシアンフィルタ処理性能に寄与する割合を確かめるために、2つともデフォルトの none に設定した状態での性能を比較した。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化13(性能が最大になる設定を探る6)
ラプラシアンフィルタIP のAXI Master が接続されているAXI Interconnect (axi_mem_intercon_1) の設定は、Slave Interface タブの Enable Register Slice を Auto に、Enable Data FIFO を 512 deep に設定した。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化14(性能が最大になる設定を探る7、まとめ)
メモリベースのラプラシアンフィルタ処理のCソースコードを高位合成した際のラプラシアンフィ ルタの処理時間をまとめておこう。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化15(性能が最大になる設定を探る8、追加1)
コメント欄でラプラシアンフィルタのCソースコード例を示してくれたおるさんのコードを元に、 tu1987さんがC++ソースコードを書いてくれた。
今回の修正は、一旦輝度に変換せずにRGB値で値を持って、使うときにRGB-Y変換をするということだ。使うときにRGB-Y変換をするので、RGB-Y変 換モジュールは1つから3つに増えているはずだが、一旦、1ライン分、RGB-Y変換をするパスがなくなるので、速くなるはずだ。
Vivado HLS 2014.4 で合成したラプラシアンフィルタIPの高速化16(性能が最大になる設定を探る8、追加2)
前回は、コメント欄でラプラシアンフィルタのCソースコード例を示してくれたおるさんのコード を元に、tu1987さんが書いてくれたC++ソースコードをVivado HLS 2014.4 で高位合成し、IP化して、シミュレーションを行った。
今回は、インプリメントを行い、ZYBOでテストする。

連続ラプラシアンフィルタ処 理
ラプラシアンフィルタを連続実行するビットをセットして、ラプラシアンフィルタの連続実行を 行った。

Vivado HLS 2014.4 で AXI4-Stream をテストする1(準備編)
次からは、AXI4-Stream でのフィルタの作り方を勉強していこう。これからは、Cソースコードというソフトウェアの書き方ではなく、例えば、シフトレジスタになるCやC++の記述を書いていくこと になる。つまり、AXI4-Master では、どういう形のハードウェアなるのか?ということに思いを馳せても、ソフトウェアとして書いてきたが、AXI4-Streamでは、クロックによる遅延素子のレジスタ を意識して書くことになるので、HDLを書いていることになるはずである。
Vivado HLS 2014.4 で AXI4-Stream をテストする2(1次元のフィルタのテスト1、C++ソースコードの公開)
今度の目的は、AXI4-Stream を使ったラプラシアンフィルタをC++をソースコードとした高位合成で作製するのだが、さいしょの段階として、高位合成がどのようなHDLを生成するのかを確認するために 最初に1次元のフィルタで試してみようと思う。
tu1987 さんのラプラシアンフィルタのC++ ソースコードを参考にさせて頂いて、インチキな myfilter() を書いてみた。トップのファイル名は fil_axis_sample.cpp とした。
Vivado HLS 2014.4 で AXI4-Stream をテストする3(1次元のフィルタのテスト2、C++シミュレーション、高位合成)
前回は、C++ ソースコードを貼ったので、今回はそれをVivado HLS 2014.4 でC++ シミュレーションと高位合成を行った。

FPGAマガジンNo.9 に記事を書きました
FPGAマガジンNo.9 に、”【365日間の評価ライセンスが取得できる!】 C言語からFPGAを開発できる高位合成ツールが無償で使える! Vivado WebPACK EditionとVivado HLS評価版のインストール手順”という記事を書きました。

Vivado HLS 2014.4 で AXI4-Stream をテストする4(1次元のフィルタのテスト3、RTLシミュレーション)
RTLシミュレーションを行った。その際に、RTLのトレースファイルを出力させて、 Vivado でシミュレーション波形の表示を行った。
Vivado HLS 2014.4 でサイドチャネル付き AXI4-Stream をテストする1(C++ソースコードの公開)
今回は、サイドチャネル付きの AXI4-Stream をテストしてみよう。AXI4-Stream のサイドチャネルとはなにか?と言うと、AXI4-Stream には、TKEEP, TSTRB, TUSER, TLALST, TID, TDEST などの信号が定義されている。
これを使用して、画像のフレーム同期を取ってみよう。AXI VDMAでは TUSER が MM2S, S2MM とも start-of-frame としてドライブされている。更に TLAST もラインの終わりにアサートされている。
Vivado HLS 2014.4 でサイドチャネル付き AXI4-Stream をテストする2(C++シミュレーション、高位合成)
サイドチャネル付き1次元俺様フィルタのC++シミュレーションと高位合成を行った。
Vivado HLS 2014.4 でサイドチャネル付き AXI4-Stream をテストする3(RTLシミュレーション)
前回、サイドチャネル付き1次元俺様フィルタのC++シミュレーションと高位合成を行ったの で、今回は、RTLシミュレーションを行って、ハードウェアでの動作を確認した。その際に、RTLのトレースファイルを出力させて、Vivado でシミュレーション波形の表示を行った。

Vivado HLS 2014.4 でAXI4-Stream版ラプラシアンフィルタIP を作製する1(C++ ソースコードの公開)
1次元の俺様フィルタを元にラプラシアンフィルタを作製する。
tu1978 さんのサンプルをほとんどコピーしながらも、自分なりのAXI4-Stream版ラプラシアンフィルタのC++ ソースコードを作製した。
Vivado HLS 2014.4 でAXI4-Stream版ラプラシアンフィルタIP を作製する2(C++シミュレーション、高位合成)
前回は、AXI4-Stream 版のラプラシアンフィルタIP のC++ ソースコードを公開した。但し、シミュレーションを速くするために、HORIZONTAL_PIXEL_WIDTH = 50、VERTICAL_PIXEL_WIDTH = 10 とした。今回は、そのC++シミュレーションと高位合成を行った。
Vivado HLS 2014.4 でAXI4-Stream版ラプラシアンフィルタIP を作製する3(RTLシミュレーション)
RTLシミュレーションを行って、ハードウェアでの動作を確認した。その際に、RTLのトレー スファイルを出力させて、Vivado でシミュレーション波形の表示を行った。
Vivado HLS 2014.4 でAXI4-Stream版ラプラシアンフィルタIP を作製する4(RTLシミュレーション2)
前回は、クロック周期を 10 ns つまり 100 MHz で高位合成を行った。今回は、動作周波数の限界に挑戦してみようと思う。
Vivado HLS 2014.4 でAXI4-Stream版ラプラシアンフィルタIP を作製する5(IP化)
前回は、動作周波数を 100 MHz から 150 MHz にすることで、性能が 1.49 倍に向上した。今回は、シミュレーション用に少ないピクセルの行列でやっていたのを 800 x 600 ピクセルに戻して、高位合成、IP 化を行った。

Vivado HLS 2014.4 vs Vivado HLS 2015.1(AXI4-Stream版ラプラシアンフィルタ IPの比較)
AXI4-Stream版ラプラシアンフィルタ IPで、Vivado HLS 2014.4 と Vivado HLS 2015.1 の高位合成結果を比較してみた。

AXI4-Stream Switcher IP の製作1(CPP ソースコードの公開)
AXI4-Stream Switcher IP の製作を行う。
AXI4-Stream Switcher IP は、”AXI4-Stream版ラプラシアンフィルタIPのカメラ表示システム1(構想編)”のブロック図に示してあるが、ラプラシアンフィルタを通した画像データの AXI4-Steram とカメラの画像データのAXI4-Steram を切り替える。
AXI4-Stream Switcher IP の製作2(Cシミュレーションと高位合成)
前回、貼ったC++のソースコードを使用して、今回は、Cシミュレーションと高位合成を行っ た。
AXI4-Stream Switcher IP の製作3(C/RTLコシミュレーションとIP化)
前回は、Cシミュレーションと高位合成を行った。今回は、C/RTLコシミュレーションをし て、その波形をVivado 2015.1で観察し、IP化を行った。

Vivado HLSの高位合成結果をHDLとして利用する1(準備編)
Vivado HLS はAXI4バスのプロトコルを C や C++ から、とっても便利に使用することができる。コードをろくに書かなくてもAXI4バスの機能を使うことができるのをこのブログでも書いてきた。それじゃ、CやC++ で書いて高位合成したHDLを普通のHDLとして使うことができるかを検証していきたいと思う。
+1した値を返すだけの簡単なC++ソースコードで高位合成後にHDLとして使うことができるのか?を検証することにした。
Vivado HLSの高位合成結果をHDLとして利用する2(ap_ctrl_none)
今回は、ap_ctrl_none を利用して、よりHDLソースコードとして使えるようにしていく。使用するVivado HLS のバージョンは 2014.4 だ。
ブロックレベルのインターフェースを ap_ctrl_none にすると、ap_start, ap_idle, ap_ready, ap_done 信号が無くなって、よりHDLソースコードとして利用しやすくなる。
Vivado HLSの高位合成結果をHDLとして利用する3(register その1)
前回は、組み合わせ回路をHDLソースコードとして使えるように、ap_ctrl_none を使用してブロックレベルの制御信号 ( ap_start, ap_idle, ap_ready, ap_done ) を削除した。
今回は、INTERFACE ディレクティブに register オプションを入れて、I/O の入力をFFで受けて、出力をFFで出力する。
Vivado HLSの高位合成結果をHDLとして利用する4(register その2、ap_hs)
前回の続きということで、ブロックレベルのINTERFACE を ap_ctrl_none に戻して、PIPELINE ディレクティブを追加してやってみよう。入出力ポートのINTERFACE は ap_none のままだ。
次に、PIPELINE ディレクティブはそのままに、 ap_none を valid 信号と ack 信号があるINTERFACE の ap_hs に変更したハンドシェーク信号が付いたケースをやってみた。
Vivado HLSの高位合成結果をHDLとして利用する5(sqrt())
今まで、Vivado HLS 2014.4 の高位合成結果をHDLとして利用する方法を見てきた。やっていることは入力データを +1 して出力データとして出力する単純な計算だったので、一度、sqrt() をやってみることにした。
倍精度平方根演算になってしまったので39クロックもかかってしまった。
Vivado HLSの高位合成結果をHDLとして利用する6(sqrt() その2)
今回は、平方根の演算を倍精度小数点演算から単精度浮動小数点演算に変更した。

Vivado HLS で cos() を高位合成
Vivado HLS で cos() を高位合成してみた。
Vivado HLS で log() を高位合成
Vivado HLS で log() を高位合成してみた。

Vivado HLS 2014.4 でディスプレイ・コントローラを作る1(高位合成、C/RTLコシミュレーション)
まだ、AXI4-Stream 版ラプラシアンフィルタIP の実装の途中なのだが、Vivdo HLS 2014.4 でディスプレイ・コントローラを作り始めてしまったので、こっちを先に書くことにする。
ディスプレイ・コントローラをC++ で書いて高位合成し、きちんとハードウェアになることを検証した。
Vivado HLS 2014.4 でディスプレイ・コントローラを作る2(RTLシミュレーション)
return ポードの HLS INTERFACE を ap_ctrl_none にした状態で、つまり、ap_start, ap_done, ap_idle, ap_ready を取り払った状態で display_cont_sub() の高位合成された Verilog HDL ソースコードが自動的にループして画像の信号を出し続けるのか?に興味がある。そこで、Verilog HDLファイルをテストベンチを作製して、RTLシミュレーションすることで解明する。
Vivado HLS 2014.4 でディスプレイ・コントローラを作る3(実機でテスト)
前回、RTLシミュレーションをして、display_cont_sub も1フレーム終了しても、次のフレームを実行することが分かった。今回は、実際にZYBOでVGAポートに画像を表示させた。
表示はできたが、フレームの最後に余計な1クロックが入ってしまう。
Vivado HLS 2014.4 でディスプレイ・コントローラを作る4(PIPELINEディレクティブのrewindオプション)
前回で終わりにするつもりだったのだが、ツィッターで、waka3_m さんにPIPELINEディレクティブのrewind オプションの事を教えて頂いたので、やってみることにした。
ZYBOをコンフィギュレーションして、ディスプレイに表示してみたところ、左上に赤、右上に緑、左下に青、右下に白が表示された。
前回のVGA出力はメイン・ディスプレイではきちんと写ったが、サブ・ディスプレイでは、一番上のラスタの右端が少し歪んでいたのだが、今回の表示は完璧だ。 良かった。。。

SDKにVivado HLSで作製したIPのドライバをインポートする
SDKにVivado HLSで作製したIPのドライバをインポートする方法について書いている。但し、通常はVivado HLSのIPをVivado のブロックデザインにインポートして、インプリメントし、SDKにハードウェアをエクスポートすれば、ドライバが使えるようになるはずなのだが、何らかの原因で使えない場 合はこれを試してみると良い。
ラプラシアンフィルタのソフ トウェアとハードウェアの速度の比較
Vivado HLSで使用したCソースコードを使用したらソフトウェアでは、どのくらい速くなるのかやってみた。
今まで、ソフトウェアでの結果とハードウェアにオフロードした時の結果を比較していたが、ソフトウェアはいかにもソフトウェアで書くようなコードで比較してい て、ハードウェア化するコードではなかった。ハードウェア化するコードをソフトウェアで実行するとどのくらいの性能になるかを検証することにした。
ラプラシアンフィルタのソフ トウェアとハードウェアの速度の比較2
前回は2つのVivado HLS 2014.4 で使用した2つのCソースコードをソフトウェアに適用したら、どの程度の処理速度になるかを調べた。Vivado HLS 2014.4 で使用したコードをソフトウェアに移行したら速くなることが分かった。更に、ほとんど同一のCソースコードによるソフトウェアとハードウェアでのラプラシアンフィルタの処 理速度の違いを測定した。
ソフトウェアのCソースコー ドをVivado HLS 2014.4 で高位合成したIPをシミュレーション
今回は、”ラプラシアンフィルタのソフトウェアとハードウェアの速度の比較2”で高位合成した IPをシミュレーションしてみた。
ラプラシアンフィルタのソフ トウェアとハードウェアの速度の比較3
今回はVivado HLS 2014.4 で最速の性能をたたき出しているCソースコードをZYBOのLinuxで動作するソフトウェアとして性能を測定した。

Vivado HLS 2014.4 でHLSストリームを使用してビデオ信号を入出力する
 lap_filter_rgb.cpp を作ったが、このファイルのシミュレーションをどうやってやるのか考えていた。
lap_filter_rgb.cpp には、HSYNCやVSYNC、VDEやpDATAなどのスティミュラスを与える必要がある。与えるためにはテストベンチに制御を残しておく必要があるが、 lap_filter_rgb.cpp をコールしてからどうやって、それらのスティミュラスを作ろうか?スレッド立てるのも方法だろうし、スティミュラスをすべて配列に保存しておいて、 lap_filter_rgb.cpp に読んでもらっても良いかも?
調べてみるとVivado HLS にHLSストリームというライブラリがあって、ストリームとして扱えるようになっている。この例はAXI4 Streamで使っている。今回は、独自のtemplate を作って、ビデオ信号の入出力を試みることにした。
Vivado HLS 2014.4 でHLSストリームを使用してビデオ信号を入出力する2
前回は、Vivado HLSのHLSストリームを使用して、ビデオ信号からラプラシアンフィルタ処理をして、ビデオ信号として出力するC++のソフトウェアを作った。今回はテストベンチを作っ てシミュレーション、CからHDLへ合成したが、クロック周期の制約が 10 ns に対して、24.6 ns になってしまった。
シミュレーションを行い、シミュレーション波形を拡大すると、5クロックで1ピクセルを処理していた。これでは使えない。

Vivado HLSの INTERFACE m_axi ディレクティブのオプション
Vivado HLS の AXI4 Master インターフェース生成用のディレクティブ INTERFACE m_axi ディレクティブにoffsetオプションが増えていた。これで、AXI4 Master アクセスするためのアドレスを設定することができる。

Vivado HLS 2014.4 を使ったAXI4 Master版のラプラシアンフィルタ
AXI4 Master版ラプラシアンフィルタだが、なかなかシミュレーションすることができなかった。今回は、”Vivado HLSの INTERFACE m_axi ディレクティブのオプション”でわかったことを使って、CシミュレーションもC/RTL協調シミュレーションもできるようにした。
テストベンチでラプラシアンフィルタに入力するデータは A という文字でそれがラプラシアンフィルタを通ってエッジになればOKというものだ。

Vivado HLS勉強会第1日目
昨日は、Vivado HLS勉強会の第1日目でした。いろいろと問題点が浮かび上がってきました。
Vivado HLS勉強会第2日目
今日はAXI4 バスを生成するというお題でした。AXI Lite Slave, AXI Master, AXI Stream。

Vivado HLSでAXI4 Master IPを書いた時のバースト転送の条件
Vivado HLS で AXI4 Master IP を書いた時のバースト転送の条件は、ユーザーズガイドによると memcpy() を使った時にバースト転送しますと書いてあるが、どうやらそうでもないようだ。

Vivado HLS によるアンシャープマスクキング・フィルタの作製1(準備編)
今までラプラシアンフィルタを作ってきたが、違うフィルタをVivado HLS 2014.4 で作ってみることにした。
アンシャープマスキング・フィルタを作って見ようと思う。インターフェースはAXI4-Stream とする。
Vivado HLS によるアンシャープマスクキング・フィルタの作製2(floatで実装してみた)
今回はZYBO 用のアンシャープマスキング・フィルタのプロジェクト unsharp_mask_14_4 をVivado HLS 2014.4 で作製した。
浮動小数点型で実装した。ソースコードを貼ってある。
Vivado HLS によるアンシャープマスクキング・フィルタの作製3(固定小数点で実装してみた)
前回はfloat でアンシャープマスキング・フィルタを実装してみたが、リソース使用量が 100% を超えてしまって、ZYBOに実装できなかった。今回は float を止めて固定小数点で実装した。
Vivado HLS によるアンシャープマスクキング・フィルタの作製4(固定小数点で実装してみた2)
前回は、float で実装したアンシャープマスキング・フィルタを固定小数点で実装した。その結果、FPGAのLUT リソース使用量が 1/33 になり、FPGAに実装可能となった。
今回は、アンシャープマスキング・フィルタのC/RTLコシミュレーションを行って、IP化を行う。
Vivado HLS によるアンシャープマスクキング・フィルタの作製7(C++ の任意精度固定小数点型)
今回は、Vivado HLS に備わっている C++ の任意精度固定小数点型で書いてみようと思う。C++ソースコード有り。
Vivado HLS によるアンシャープマスクキング・フィルタの作製8(C++ の任意精度固定小数点型2)
前回はC++のソースコードを公開した。今回は、Cシミュレーションを行ってから、C++ から HDL への合成を行って、int 型でシフトを使って演算した実装と比較した。
Vivado HLS によるアンシャープマスクキング・フィルタの作製9(C++ の任意精度固定小数点型3)
前回、int 型で予め左シフトして小数を整数にして演算するよりも、固定小数点型にしたほうが、LUT 使用量は減ったが、FF 使用量は増えた。
今回は、固定小数点型で更にリソース使用量の削減、レイテンシの削減を図る。使用しているのは Vivado HLS 2014.4 。
Vivado HLS 2015.3 の半精度浮動小数点数でアンシャープマスキング・フィルタを作った
Vivado HLS 2015.3 の半精度浮動小数点数でアンシャープマスキング・フィルタを作った。
float で実装した時と比べると、リソース使用量は減っているが、やはりリソース使用量は多いといえる。Zynq-7010 には入らない。
Vivado HLS によるアンシャープマスクキング・フィルタの作製10(ap_int 型による固定小数点)
”Vivado HLS によるアンシャープマスクキング・フィルタの作製8(C++ の任意精度固定小数点型2)”で、int 型で予め左シフトして小数を整数にして演算するコードを書いた。
今回は、ap_int 型で桁を制限してリソース使用量の低減を図った。

DSF2015 C-6 でのVivado HLS で生成したAXI4-Master IPの簡単な例について
DSF2015 の C-6 ”Xilinx社のFPGAにおける高位合成ツールVivado HLSの効果と性能”で説明したAXI4 Masterインターフェースの例をブログで説明したいと思います。

Vivado HLS 2015.3 が出た
今度のVivado HLS は1つのテストしかしていないが、今まで使ってきたVivado HLS 2014.4 よりも良くなっていると思う。今やっている固定小数点型の比較が終わった時点でVivado HLS 2015.3 に乗り換えたいと思う。
Vivado HLS 2014.4 vs Vivado HLS 2015.1 vs Vivado HLS 2015.3(AXI4-Stream版ラプラシアンフィルタ IPの比較)
AXI4-Stream版ラプラシアンフィルタ IPで、Vivado HLS 2014.4 と Vivado HLS 2015.1 と Vivado HLS 2015.3 の高位合成結果を比較してみた。
Vivado HLS 2015.3 は FF の使用量は多いものの、LUTの使用量は少ない。但し、クロック周期 2.5 ns を除けば、FF とLUT の数は大体同じようなので、バランスが良いと言える。今後はVivado HLS 2014.4 の代わりにVivado 2015.3 を使いたいと思う。

Vivado HLSにおける固定小数点の誤差を平均2乗誤差で算出する
Vivado HLS 2014.4 で int 型で予め左シフトして小数を整数にして演算したり、固定小数点型を使って小数点を含んだ演算をしてきた。今までフィーリングでこれで大丈夫かな?と判定してきたが、流石に なにか判定基準が欲しい。
そこで、平均2乗誤差を導入することにした。平均2乗誤差 MSE (mean squared error) を次に式で求めることにする。

アンシャープマスキング・ フィルタによる Vivado HLS 2014.4 と Vivado HLS 2015.3 の比較
アンシャープマスキング・フィルタのC++ソースコードによって、Vivado HLS 2014.4 とVivado HLS 2015.3 を比較してみた。
Vivado HLS 2015.3 でアンシャープマスキング・フィルタのC/RTL コシミュレーション
Vivado HLS 2015.3 でアンシャープマスキング・フィルタのC/RTL コシミュレーションをやってみた。
Vivado HLS 2015.3 でアンシャープマスキング・フィルタのIP化
int 型で予め左シフトして小数を整数にして演算するプロジェクトをIP化した。

Vivado HLS 2015.4を試してみる(AXI4-Stream版ラプラシアンフィルタ IPを使用した)
以前、”Vivado HLS 2014.4 vs Vivado HLS 2015.1 vs Vivado HLS 2015.3(AXI4-Stream版ラプラシアンフィルタ IPの比較)”という記事で、Vivado HLS 2014.4 vs Vivado HLS 2015.1 vs Vivado HLS 2015.3 を比べたことがあった。これらと比較しても良いのだが、AXI4-Stream版ラプラシアンフィルタ IP が青のみ出力されてしまっていた関係で修正が入っているので、修正後のCソースコードでやってみることにした。

Vivado HLSのI/Oプロトコル(ブロックレベルとポートレベル)
今日は、Vivado HLS のI/O プロトコルにに付いて書いてみたいと思います。
ソフトウェアの C、C++ がHDL 、つまりハードウェアになるので、時間の概念が入ってきます。つまり、ソフトウェアは関数コールで関数を呼び出して実行させますが、ハードウェアはそこに回路の実体ができ ちゃってます。つまり関数をコールする、しないにかかわらず、いつもお仕事をできる、しちゃえる状態にあるわけです。その回路を何らかの条件で始まりを指示す る必要あります。つまり、C の関数の引数の信号線だけではなく、追加の信号も必要になるということです。
これらの信号は、Vivado HLS でHDL へ変換する過程で付加されます。ですので、C をVivado HLS で高位合成して、HDL を見ると見慣れない余計な信号があるのが見えると思います。

Vivado HLS 勉強会1(基礎編)を公開しました
Vivado HLS 勉強会資料の 1 番目の”Vivado HLS 勉強会1(基礎編)”を公開しました。

Vivado HLSで幅の異なる ap_int の演算結果を検証してみた
Vivado HLS で幅の異なる ap_int の演算結果を検証してみた。
ap_uint、ap_int 同士のビット幅の異なる演算も問題なく処理されるようだ。

Vivado HLS 勉強会2(レジスタの挿入とPIPELINEディレクティブ)を公開しました
”Vivado HLS 勉強会2(レジスタの挿入とPIPELINEディレクティブ)”を公開しました。
今回は、ディレクティブを使って、入力、そして出力にレジスタを挿入して、PIPELINEディレクティブを入れてパイプライン化します。
次にPIPELINEディレクティブの応用として、rewind オプションを使ってディスプレイ・コントローラを実装してみます。

Vivado HLSでクロック周期を2.5ns で合成した掛け算回路は本当に400MHzで動作するのか?
SlideShare で公開している”Vivado hls勉強会2(レジスタの挿入とpipelineディレクティブ)”の 70 ページの Solution から Vivado HLS でクロック周期が 2.5 ns つまり 400 MHz で動作するように設定して高位合成を行っているのだが、本当に400 MHz で動作するのか?をVivado 2015.4 でプロジェクトを作製してテストしてみた。
テストの結果は、約600MHzで動作するという結果になった。

Vivado HLS勉強会3(AXI4-Lite Slave)を公開しました
Vivado HLS 勉強会3 (AXI4 Lite Slave)をSlideShare に公開しました。
内容は、
Vivado HLS 2015.4 を使用して、今までやってきた掛け算回路をAXI4 Lite Slaveインターフェースで実装します。
Vivado HLSでIP化を行って、Vivado 2015.4のIPIを使用してZYBOに実装します。
Vivado HLSで自動的に作製されたドライバを使用して、アプリケーションを作製し、掛け算回路を制御します。
ZYBO実機で掛け算回路を動作させます。シリアル・ターミナルで掛け算を行います。

Vivado HLS 2014.4 と Vivado HLS 2015.4 の性能差(ソフトウェア的に書いたラプラシアンフィルタで検証)
Vivado HLS勉強会4 (AXI4 Master)をVivado HLS 2014.4 対応から Vivado HLS 2015.4 対応に変更した時に、ソフトウェア的に書いたラプラシアンフィルタのCソースコードを高位合成した結果が異なったので、書いておく。

Vivado HLS勉強会4(AXI4 Master)を公開しました
今年の第一弾として、SlideShare に Vivado HLS勉強会4(AXI4 Master)を公開しました。
内容はと言うと、AXI4 Master インターフェースを使用した3つのCソースコードの実装のラプラシアンフィルタを高位合成し、C/RTLコシミュレーションで性能を比較します。
残念ながら、実機確認はありません。ご自分でFPGAの部屋のブログ記事を見ながら実装してみてください。
後、AXI4バスの知識が必須です。
Vivado HLS勉強会5(AXI4 Stream)を公開しました
最後のVivado HLS勉強会資料になります。
Vivado HLS で AXI4 Stream インターフェースを使用する方法です。AXI4 Stream がAXI4 バスを使用するときの王道になると思っています。
フィルタを作る場合に、メモリからのDMAはXilinx 社のIP を使用して、フィルタ部分のソースコードだけをVivado HLS で作製するのが、今のところ最適化しやすくて良いと思っています。
なお、AXI4 Stream 編ではStream が使えるように、C++ を使用しています。

hls::LineBufferとhls::Windowでラプラシアンフィルタを実装する1
あるところから hls::LineBuffer と hls::Window を教えて頂いたので、それを使ってラプラシアンフィルタを実装してみました。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する2
前回は、hls::LineBuffer と hls::Window を教えて頂いたので、それを使ってラプラシアンフィルタを実装した。今回は、そのC++ソースコードをディレクティブを追加してチューンアップしていく。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する3
今回は、conv_rgb2y() のインスタンス数を削減してどうなるか?を見てみたい。C++ ソースコードをわずかながら書き換えた。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する4
今回は、ピクセルの読み込み、ピクセルの書き込みで memcpy() を使った実装を試してみた。まずは、if 文を使って、最初に1ライン分ピクセルを読み込んで、最後に1ライン分のラプラシアンフィルタ処理結果を書き出す方法でやってみた。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する5
前回は、列の処理と、行の処理の2重 for ループの内側の行の処理の for ループに 最初の行のピクセルを処理する時は、if 文で1ライン分 memcpy() で Read して、行の最後のピクセルを処理した後で、if 文で1ライン分のピクセルを memcpy() でWrite する。
今回は、単純にmemcpy() を内側の for ループの外に置くことにする。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する6
前回は、単純にmemcpy() を内側の for ループの外に於いた実装を試した。今回は memcpy() の代わりに for 文で1行分 Read, Write を行う実装を試してみた。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する7
前回は、 memcpy() の代わりに for 文で1行分 Read, Write を行う実装を試してみた。今回は、2 つの実装を実際に使用する 800 x 600 ピクセルの解像度に変更して、どの位リソースを使うかと、今までは 100 MHz で合成してきたが、どの位の動作周波数で合成できるかを探ってみた。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する8
前回までで、AXI4 Master 版は終了として、今回は、AXI4 Stream 版で hls::LineBufferとhls::Window を使用して実装してみようと思う。
hls::LineBuffer とhls::Windowでラプラシアンフィルタを実装する9
今回は、AXI4 Stream 版の hls::LineBuffer と hls::Window を使用したラプラシアンフィルタが動作周波数がどこまで行けるかを確かめる。この AXI4 Stream 版のラプラシアンフィルタは、”Vivado HLS の LOOP_TRIPCOUNTディレクティブ”を使用して、高位合成時のLatency や Interval を表示できるようにしている。

Vivado HLS の LOOP_TRIPCOUNTディレクティブ
ループで実行 される反復回数の合計を指定する LOOP_TRIPCOUNT ディレクティブの使い方を紹介する。

Vivado HLS 2015.4 で OpenCV を使ってみた1
Vivado HLS 2015.4 で OpenCV を使ってみようということで、やってみた。問題なく使える。
Vivado HLS 2015.4 で OpenCV を使ってみた2(テストベンチに Mat を使って実装した)
前回のOpenCVコードの正解というか、書き方は、”Accelerating OpenCV Applications with Zynq-7000 All Programmable SoC using Vivado HLS Video Libraries”の英語資料に詳しく書いてあった。という訳で、前回のコードを書き換えた。
それとは別にテストベンチを OpenCV 2.X のMat フォーマットを使う書き方に変更したいという欲求があって、いろいろと試していたが、上手く行ったので、書いておく。
Vivado HLS 2015.4 で OpenCV を使ってみた3(Sobelフィルタを試した1)
前回はテストベンチをOpenCV 2.X のMat で書き直した。今回はSobel フィルタを試してみた。
初めにカラーの状態でSobel フィルタを試してみたところ、上手く行ったのだが、GRAY変換してSobel フィルタを掛ける所で、いろいろと試行錯誤してしまった。
Vivado HLS 2015.4 で OpenCV を使ってみた4(Sobelフィルタを試した2)
前回はC シミュレーションまでだったので、今回は、Cコードの合成、C/RTL コシミュレーションを行った。
Vivado HLS 2015.4 で OpenCV を使ってみた5(Sobelフィルタを試した3)
前回は、X 軸方向のSobel フィルタをやっていたのだが、今回は Y 軸方向のSobel フィルタをテストしてみる。
Vivado HLS 2015.4 で OpenCV を使ってみた6(Sobelフィルタを試した4)
前々回はX軸方向のSobel フィルタ、前回はY軸方向のSobel フィルタをやってみた。今回はXY軸方向のSobel フィルタをやってみた。

Vivado HLS 2015.4 で OpenCV を使ってみた7(FAST Corners Detection 1)
前回までは、Sobel フィルタの動作について試してみたが、今回は、その次の”FAST Corners Detection”を試してみる。
Vivado HLS 2015.4 で OpenCV を使ってみた8(FAST Corners Detection 2)
前回は、C シミュレーションまで行った。今回は、C コードの合成とIP化を行った。

Vivado HLS 2016.1 で OpenCV の Sobel フィルタを試してみた
Sobel フィルタをVivado 2016.1 でやってみた。

Vivado HLS勉強会資料(AXI4 Lite Slave)を更新しました
ZYBO_zynq_def.xml を使用してZYBO のPS部分を設定していましたが、Digilent社のWebサイトにZYBO_zynq_def.xml が無くなってしまったので、ボード・ファイルを使う方法に変更しました。

Vivado HLS を使用した車の白線検出1(初めに)

車の白線検出をハードウェア化してみたいということで、OpenCVを使用して車の白線検出を 行い、それをVivado HLS でハードウェア化してみることにした。
Vivado HLS を使用した車の白線検出2(HoughLinesで直線検出)
前 回、”ka367/Lane-Detecting-Using-Hough-Transform”のコードを試してみたが、C シミュレーションは上手く行かずに、C コードの合成はZYBO に入らなかった。そこで、地道にOpenCVのHough 変換をやってみることにした。
Vivado HLS を使用した車の白線検出3(暗い画像での白線検出)
前回は、”Line Detection by Hough Line Transform”のOpenCVを使用した直線検出のアプリケーションを使用して、”ka367/Lane-Detecting-Using-Hough- Transform”の”test_1080p.bmp”の道路の白線を検出することができた。
今回は、暗い時の白線を検出できるかどうかを調べてみようと思う。
Vivado HLS を使用した車の白線検出4(ヒストグラム均一化)
前回は、cannyフィルタでエッジ検出した後でHough 変換を行って、直線検出したが、最後の暗い画像では、道路の白線を検出することはできなかった。今回は、canny フィルタの前に equalizeHist() を行うことで、ヒストグラムの均一化を図ってみよう。
Vivado HLS を使用した車の白線検出5(hls::HoughLine2())
前回はヒストグラムの均一化を行ってから、グレー変換、Canny フィルタ、Hough 変換を行うと白線検出をすることができた。今回は、”Vivado HLS を使用した車の白線検出1(初めに)”で使用した”ka367/Lane-Detecting-Using-Hough-Transform”が動作して、C シミュレーションとC コードの合成をすることができた。
Vivado HLS を使用した車の白線検出6(hls::HoughLine2() その2)
前回は、HLS ビデオライブラリを使用した Hough 変換による白線検出が上手く行ったが、合成したらZYBO のリソース使用量が 2200 % 程度になってしまった。今回はリソース使用量を削減してみた。
Vivado HLS を使用した車の白線検出7(Canny フィルタ1)
前回、白線検出ハードウェアはとてもZYBO には入らないということがよく分かった。それでも Canny フィルタだけはハードウェアにしたいということでやってみた。
Vivado HLS を使用した車の白線検出8(Canny フィルタ2)
前回は、ZYBOのリソース使用量をオーバーしてしまった。今回は、その一番大きな原因である ガウシアンフィルタを 5x5 から 3x3 にしてみよう。
Vivado HLS を使用した車の白線検出9(Canny フィルタ3)
前回、ガウシアンフィルタの 5x5 では、DSP リソース使用量が ZYBO で使用できる DSP 数をオーバーしてしまうため、3x3 に変更した。しかし、よくよく考えてみると、ガウシアンフィルタや Sobel フィルタなどは、現在はカラーでファイルを掛けているが、グレー変換して1色でやっても同じことだと気がついたので、それでやってみたら、案の定、5x5 のガウシアンフィルタでもリソース使用量が減って、ZYBO に入るようになった。
Vivado HLS を使用した車の白線検出10(ラプラシアンフィルタ1)
”ZYBO 上のOpenCV で白線検出3(Canny フィルタのみの場合)”でZYBO のLinux 上でソフトウェアによる白線検出のめどはついた。
しかし、これは、ソフトウェアのみによる白線検出で、ハードウェアにオフロードにしていないのは寂しい。
エッジ強度と細線化処理を行っているが、これをラプラシアンフィルタに置き換えたらどうか?と考えてみた。ラプラシアンフィルタ処理後のエッジはすでに細線化 されているような感じだし、行けるかもしれない?ということで実際にやってみることにした。
Vivado HLS を使用した車の白線検出11(ラプラシアンフィルタ2)
前回、性能の出なかったハードウェア版Canny フィルタの代わりにラプラシアンフィルタを使用したところ白線検出の成績が良かった。今回は、自分で撮ってきたいろいろな道路の写真でラプラシアンフィルタを使用した白線 検出を行うことができるか?検証してみた。

レジスタ設定用AXI4 Master IPをVivado HLS で作ってみた
PWM モジュールIP をシミュレーションするために、レジスタ設定用AXI4 Master IPをVivado HLS で作ってみた。
レジスタ設定用AXI4 Master IPをVivado HLS で作ってみた2
前回は32 ビット長の予定のディレイ値やアドレス、データが 32 ビット長いらないということで、必要なビット幅に丸められてしまった。
今回は、ビット幅を丸められないで、32 ビット長を確保できるような reg_ad[][] の初期値を探ってみよう。

Vivado HLS 2016.2 で volatile を使用する場合
Vivado HLS で AXI4 Master IP を作る際に volatile を使ってあったので、使ってきたがVivado HLS でどのようなときに volatile を使用するのかを調べたことはなかった。今回、hiyuh さんのおかげで、volatile を使う意味が分かった。
結局、出力ポートに結果を順次結果を出すためには、入力ポートもポインタ渡しにする必要があるようだ。

PmodHB5インター フェース回路 (PmodHB5_inf) の作成
PmodHB5: H-bridge Driver with Feedback Inputs のインターフェース回路を作成することにした。
今まで作ったPWM モジュールの”Vivado HLS で PWM モジュールIP を作ってみた”と”PmodHB5 のセンサー・フィードバック処理IP を作ってみた”を合わせたIP を作ろうということだ。
PmodHB5 用のIP として 2 つの関数を一緒にVivado HLS でIP 化するのは問題があると思う。
2つのモジュールが独立に動作するので、それぞれが終了するまで関数が終了しないため、連続に動作する必要があるPWMモジュールなどがあると動作がうまく行 かない。

Vivado HLS で DMA Write IP を作る(絶対アドレス指定編)
AXI4 Master でフィルタを実装するコードを考えていると、やはり、memcpy() と中のフィルタ処理を重ね合わせられないので、すべてVivado HLS で作ると性能が出しにくい。
そこで、フィルタ部分はAXI4 Stream で作っておいて、DMA 部分は別にAXI4 Master Read - AXI4 Stream のDMA Read とAXI4 Stream - AXI4 Master Write の DMA Write の2つのIP をVivado HLS で作った方が良さそうだ。
Vivado HLS で DMA Write IP を作る(オフセット・アドレス指定編)
前回は、絶対アドレスを入れてDMA 転送を行うCソースコードを書いたが、C/RTL 協調シミュレーションで、結果のBMP ファイルがおかしくなってしまった。今回は、絶対アドレスでなくオフセット・アドレスを入れてDMA 転送を行うCソースコードを書いてみた。
Vivado HLS で DMA Read IP を作る(絶対アドレス指定版)
DMA Write IP に続いてDMA Read IP を作ってみた。絶対アドレスを設定する版を作った。

Vivado HLSで作ったDMA Write IP を実機でテスト1(インプリメント)
”Zybot のカメラ画像でGabor Filterのパラメータを取得した3(Zybotでテスト)”で実際に使用しているプロジェクトで、AXI VDMA IPと”Vivado HLS で DMA Write IP を作る(絶対アドレス指定編)”のDMA Write IP を入れ替えてテストしてみようと思う。
Vivado HLSで作ったDMA Write IP を実機でテスト2(実機テスト)
前回は、Vivado HLS で作った DMA Write IPをZYBO_0_2 プロジェクトに入れて、論理合成、インプリメント、ビットストリームの生成を行った。今回は、ハードウェアをエクスポートして、SDKでアプリケーションを作成し、 ZYBO 実機でテストしてみた。
Vivado HLSで作ったDMA Write IP を実機でテスト3(Vivado Analyzer)
前回はZYBO_0_2 プロジェクトにDMA Write IP を入れたプロジェクトでカメラの画像を表示できないという結果だった。今回は、Vivado Analyzer を使って、なぜDMA Write IP が動作しないか?を探った。その結果、原因は判明した。
Vivado HLSで作ったDMA Write IP を実機でテスト4(成功)
前回は、DMA Write IP がうまく動作しなかった原因は、画面サイズが 800 x 600 ピクセルなのに、シミュレーション用の画像サイズの 64 x 48 ピクセルに設定されていたことが原因だった。今回は、画面サイズを 800 x 600 ピクセルに修正して、IP を更新して、再度テストすることにした。

Vivado HLS でシミュレーション用と合成用の記述を書き分ける
今までは、Vivado HLS で、シミュレーションするときと合成するときの記述の切り替えは、コメントで切り分けていた。
シミュレーションするときに大きな画像などを対象とするとシミュレーション時間がかかってしま うので、できれば小さい画像を使いたい。合成時は実際に扱う画像の大きさを指定する必要があるということで、記述の切り替えを忘れてしまって痛い目を見ること がある。

Vivado HLSで作ったDMA Read IP を実機でテスト1(動作しない)
”Vivado HLSで作ったDMA Write IP を実機でテスト4(成功)”に続いて、”Vivado HLS で DMA Read IP を作る(絶対アドレス指定版)”で作ったDMA Read IP をテストする。
動作しなかった。

DMA Read IP を単体でシミュレーション1(論理シミュレーション)
”Vivado HLSで作ったDMA Read IP を実機でテスト1(動作しない)”で DMA Read IP が全く動作しないので、単体でシミュレーションしみることにした。
DMA Read IP を単体でシミュレーション2(論理合成後の機能シミュレーション)
前回はDMA Read IP を論理シミュレーションしたが、動作に問題はなかった。今回は、論理合成を行った後に論理合成後のシミュレーションを行った。
DMA Read IP を単体でシミュレーション3(DMA Read IP単体で論理合成後にシミュレーション)
前回は、DMA Read IP 、AXI4 Slave BFM、 reg_write_read IP の3つをIP Integrator に入れて、論理合成をしていたので、AXI4 Slave BFM、 reg_write_read IP のどちらかが論理合成できない可能性もある。そこで、DMA Read IP だけをブロックデザインにAdd IP して、AXI4 Slave BFM、 reg_write_read IP は、シミュレーション・ファイルにすることにした。
DMA Read IP を単体でシミュレーション4(結論)
結局、DMA_Read_test2 プロジェクトでは、Post-Synthesis Fuctional Simulation はどうやっても動かないようだ。どこか回路がおかしいのかもしれない?

memcpy() を利用したDMA Read IP 1(memcpy() が 1 個の場合)
それでは、ということで、DMA Read IP の異なる実装を試してみることにした。Vivado HLS 2016.2 を使用している。
memcpy() を使用して明示的にAXI4 のバースト転送を使用する。
memcpy() を利用したDMA Read IP 2(memcpy() が 2 個の場合)
前回はDATAFLOW 指示子を使用して、memcpy() と for 文を重ね合わせて、約1クロックで 1 データを出力させることができた。ただし、カメラ画像表示システムに入れてテストしたところ、画像を表示することができなかった。
今回は、memcpy() を使用して、1行分の画像を転送するとエラーが発生する(DATAFLOW 指示子を入れない場合)ので、1 行の半分ずつ memcpy() するようにしてみた。さらに、そこにDATAFLOW 指示子を入れてみた。なお、Vivado HLS 2016.2 を使用している。

RTLを語る会12でお話し したスライドをSlideShare にアップロードしました
”RTLを語る会(12) 〜Vivado HLS GO〜”でお話してきましたが、そのスライドをSlideShare にアップロードしました。
タイトルは”Vivado HLSのシミュレーションとHLSストリーム”です。

Vivado HLS でFIFO を作ってみた1(指示子を入れない場合)
Vivado HLS でFIFO を作ってみようと思う。
DATAFLOW 指示子が for 文にも有効ということが分かったので、それを試してみよう。最初はPIPELINE や DATAFLOW 指示子を入れないでどうなるのかを試してから入れてみようと思う。
Vivado HLS でFIFO を作ってみた2(指示子を入れた場合)
前回は、入出力数に制限のあるFIFO を作ってみたが、DATAFLOW 指示子やPIPELINE 指示子を入れてないので、input のfor 文とooutput のfor 文がシーケンシャルに実行されてしまったし、output は出力するのに 2 クロックかかってしまった。今回は、DATAFLOW 指示子とPIPELINE 指示子を入れて、どう変わるのか?を検証してみよう。
Viavdo HLS の array_FIFO Example
Xilinx 社のフォーラムの”Vivado HLS - AXI4 Stream FIFO”を見ていたら、Vivao HLS のExample として、array_FIFO があるというのがわかりました。
Vivado HLS でFIFO を作ってみた3(hiyuhさんに教えてもらった回路)
hiyuh さんにFIFO のC++ のコードを教えてもらったので、それを typedef を取って書き直した。
それが、fifo_test_2b.cpp だ。その fifo_test_2b.cpp を示す。

Vivado HLS でRGB2HSV IPを作る1(UNROLL指示子による性能向上)
Vivado HLS 2016.2 で、RGB2HSV IP を作ろうと思う。
Vivado HLS でRGB2HSV IPを作る2(Cシミュレーション)
前回はUNROLL指示子による性能向上が図れることを示したが、C ソースコードが間違っていた。現在は修正済みだ。
今回は、テストベンチを作成し、C シミュレーションを行った。
Vivado HLS でRGB2HSV IPを作る3(H の表現方法)
前回のH(色相)の画像は、 360 までの値を 255 までにスケールを変えて表示していたのだが、360 までということは円なので、0 も赤だが、360 も赤に戻る。これでは、360 までの値を 255 にスケールを変えて表示しても意味がないと思った。HSV2RGB 変換しても元の画像に戻るだけだ。そうだ、S = V = 255 としてH をHSV2RGB 変換すれば色がはっきり見えるはずではないか?ということで、やってみた。
Vivado HLS でRGB2HSV IPを作る4(C ソースコード)
今回は現在のC ソースコードを貼っておこうと思う。
Vivado HLS でRGB2HSV IPを作る5(性能とリソース使用量)
今回は、”Vivado HLS でRGB2HSV IPを作る4(C ソースコード)”で C コードの合成を行って、性能とリソース使用量を考える。

Vivado HLS 2016.3 での変更点
Vivado HLS 2016.3 の私が気が付いた主な変更点を書いておこうと思う。

Vivado HLS によるAXI4 マスタ・インターフェースのバースト転送
少なくとも、Vivado HLS 2015.4 時代からは、Vivado HLS によるAXI4 マスタ・インターフェースのバースト転送が memcpy() 関数を使うだけでなく、ある条件の for 文で AXI4 マスタポートを使用したときにも適用されるようになった。
それを試してみた。
Vivado HLS によるAXI4 マスタ・インターフェースのバースト転送2
前回は、バース ト ビヘイ ビアーを指定したにもかかわらず、バースト転送しなかった。今回はバースト転送するようにCソースコードを書き換えてみた。

AXI4-Stream向き のコードで書いたラプラシアンフィルタをVivado HLSでテスト1
”Vivado HLS のソースコードをSDx で試す4(AXI4-Stream向きのコード)”でAXI4-Stream向きのコードをAXI4 Master として実装して性能を評価したところ、とても高い性能だった。それは、DMAのWrite とRead が重なり合って実行しているとしか考えらない性能だった。となると、そのコードはVivado HLS で合成したときにDMAのWrite とRead が重なり合って実行されるのだろう。そのような状況には出会ったことがないので、さっそくVivado HLS でやってみた。
なるほど、これは凄い。こんな凄い性能が出せたんだ、Vivado HLS のAXI4 Master 。
AXI4-Stream向き のコードで書いたラプラシアンフィルタをVivado HLSでテスト2
前回は、AXI4-Stream向きのコードをAXI4 Master として実装して性能を評価したところ、理論的な限界性能だった。今回は、どのように書いたら理論的な限界性能が出るのかを探ってみる。とりあえず、Writeを変えてみよ う。
ほんの少し書き換えただけで、最高性能にほど遠くなってしまった。
AXI4-Stream向き のコードで書いたラプラシアンフィルタをVivado HLSでテスト3
前回、lap_fb[] の最初で最後の行のオール 0 を書いたらDMA Write がシングル転送になってしまった。つまり、DMA Write の書き込みの順序をいじるとバーストしなくなるんじゃないか?という疑問がわく。そこで、DMA Read の順番も、DMA Write の順番も守るようにした。DMA Read と Write の順番を守るということは、y を行数+1 回すことにして、DMA Read は最後の1回の実行を中止し、DMA Write は最初の1回の実行を停止することにした。
ReadもWriteもシングル転送になってしまった。

FPGAマガジン No.16にVivado HLSのAXI4 Masterアクセス編を書きました
FPGAマガジン No.16 にVivado HLSのAXI4 Masterアクセス編を書きました。
FPGAマガジンNo.16 のVivado HLS AXI4マスタ編のソースコード
FPGAマガジンNo.16 のVivado HLS AXI4マスタ編のソースコードをGithubの marsee101/FPGAmagagine16_Vivado_HLS_AXI4M に置いておきましたので、ご利用ください。

FASTXコーナー検出によ る物体の形状検出1(Vivado 2016.4 プロジェクト)
以前、”FASTX コーナー検出の改良3(threshold をソフトウェアで変更可能にする)”で、Vivado HLS のOpenCV 機能の一部であるFASTX コーナー検出を使用して、CMOS カメラで撮影した画像のコーナー検出を行った。
今回は、FASTX コーナー検出のプロジェクトを Vivado 2016.4 に変換して動作を確かめた。
FASTXコーナー検出によ る物体の形状検出2(Vivado HLS 2016.4 プロジェクト)
前回は、Vivado 2016.1 のカメラ画像から FASTX コーナー検出を行うプロジェクトをVivado 2016.4 に変換して動作を確認した。
今回は、後先違ってしまったが、FASTX コーナー検出を行う fastx.cpp のVivado HLS 2016.4 プロジェクトを示す。
FASTXコーナー検出によ る物体の形状検出3(FASTXプロジェクトの修正)
前回は、FASTX コーナー検出のVivado HLS 2016.4 プロジェクトをやってみた。今回は、前回のFASTX コーナー検出は元の写真が入っているので、コーナー検出された結果から物体を検索することは難しいので、コーナー検出された位置のみを表示するようにしてみた。
FASTXコーナー検出によ る物体の形状検出4(FASTXコーナー検出の点だけを表示)
前回は、FASTX コーナー検出の点だけを抽出するVivado HLS のプロジェクトを作成した。今回は、そのVivado HLS のIP をVivado のプロジェクトに入れて、カメラ画像からリアルタイムにFASTX コーナー検出の点を表示した。

Vivado HLS 2016.4 における assert() 文の効果
Vivado HLS 2016.4 で変域を指定することができる assert() 文の効果を確かめてみた。
Vivado HLS 2016.4 における assert() 文の効果2
前回は、assert() はfor ループのカウント用変数の変域を与えられるが、通常の変数の変域を指定できるわけでは無いという結論になったが、hiyuh さんに再度教えてもらって、もう一度やってみた。
Vivado HLS 2016.4 における assert() 文の効果3
前回も assert() 文を使用して、演算に使用する変数の変域を指定することにより、任意精度固定小数点型の飽和演算は必要ないとVivado HLS に認識してもらい、しかもビット長も制限されることでリソース使用量の低減を図ってきた。しかし、ループカウンタのカウント数の制限によってリソース使用量が低減はされた が、任意精度固定小数点型の通常の演算では assert() 文が効いていなかった。
もう一度、hiyuh さんに教えてもらってやってみた。
Vivado HLS 2016.4 における assert() 文の効果4(自分で定義した固定小数点)
これまでは、任意精度固定小数点型で assert() 文で変数の変域を指定するリソース使用量の低減効果を見てきたが、今回は、任意精度固定小数点型を使用しない自分で定義した固定小数点演算との比較をしてみた。
Vivado HLS 2016.4 における assert() 文の効果5(AXI4-Stream版での比較)
前回は、アンシャープマスキング・フィルタ単体では、任意精度固定小数点型の方が自分で定義し た固定小数点型に比べてリソース使用量が少なくなったという結果だったが、AXI4-Stream インターフェースを被せた状態ではどうなるか?をやってみた。

Vivado HLS 2016.4 でUNROLL指示子を試してみた
Vivado HLS 2016.4 でUNROLL指示子を試してみた。
UNROLL指示子については、Vivado HLS のユーザーズガイド、”高位合成 UG902 (v2016.4) 2016 年 11 月 30 日”の 133 ページの”最適なループ展開によるパイ プ ラ イ ンの改善”を参考にした。

Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)
”Vivado HLS で DMA Read IP を作る(絶対アドレス指定版)”では、DMA Read IPを作成したが、”Vivado HLSで作ったDMA Read IP を実機でテスト1(動作しない)”で実機で動作を確認しても動作しなかった。
”DMA Read IP を単体でシミュレーション3(DMA Read IP単体で論理合成後にシミュレーション)”では、DMA Read IPを単体でシミュレーションしたが、論理シミュレーションはそれらしく動いても Post-Synthesis Fuctional Simulation では、動作しないという問題があった。これは、IOがオーバーフローしているからかもしれないということで、Vivado 2016.4 でテストしてすることにした。
「Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)」を使って合成後の機能シミュレーション
前回は絶対アドレス指定のDMA Read IPをVivado HLS 2016.4 で作成した。今回は、そのDMA Read IPをVivado で論理シミュレーションと合成後の機能シミュレーションを行った。
「Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)」を使って合成後の機能シミュレーション2
ikwzm さんにVivado HLS のExport RTL のEvaluate Generated RTL をVHDL にしたら論理合成後の機能シミュレーションも動いたということでやってみたのだが、やはり結果は同様に動作していなかった。
「Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)」を使って合成後の機能シミュレーション3
前回は、Vivado HLS 2016.4 で Verilog でIP をExport RTL して、Vivado 2016.4 では、Target language を VHDL にしたら、Post-Synthesis Functional Simulation が正常になった。ここでは、IO ピンが足りるようにVirtex7 の xc7vx980tffg1928-2 を使用していたが、IO ピンが足りないZYBO (xc7z010clg400-1)ではどうか?を確かめてみた。ikzwm さんがやってくれたので、大丈夫とは思うが自分でも確かめてみる。

ikwzm/vivado- hls-axi-dma-read-failureを試してみた
以前、「Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)」をIP として入れたVivado プロジェクトを論理シミュレーションすると動作するが、 Post-Synthesis Functional Simulation すると動作しない。しかし、Project Settings のTarget language を VHDL にする(DMA Read IPはVerilog HDL で IP化しているのだが)と Post-Synthesis Functional Simulation が動作するという現象があった。それを ikwzm さんが vivado-hls-axi-dma-read-failure でテストケースを作ってくれたのだが、Linux にVivado 2016.4 の環境が無かったためやっていなかった。今回は、環境を構築したためやってみた。

Vivado HLS で DMA Write IP を作る2(絶対アドレス指定編)
”Vivado HLS で DMA Write IP を作る(絶対アドレス指定編)”のテストベンチが間違っていたので、その修正です。その他のC ソースコードも修正してあります。
Vivado HLS で DMA Read IP を作る3(オフセット・アドレス指定版)
”Vivado HLS で DMA Read IP を作る2(絶対アドレス指定版)”は絶対アドレスを3つ指定して、DMA Read を行うが、DMA Read IP のオフセット・アドレス指定版はベース・アドレスを指定し、ベースアドレスに対してのオフセット・アドレスを3つ指定してDMA Readするアドレスを決定する。ただし、C のソースコードはm_axi 指示子の depth と offset オプションのみが違っている。
depth は本来の値に設定する。そして、offset=slave とする必要がある。offset=slave とすると、ベース・アドレスがAXI4-Lite のレジスタとして実装される。

Vivado HLSのAXI4マスタ機能のオプションの違いによるテストベンチからの呼び出し方法
ちょっと訳があって、Vivado HLSのAXI4マスタ機能のオプションの違いによるテストベンチからの呼び出し方法を書いておく。

FPGAマガジンNo.17 にVivado HLS の記事を書きました(ソースコードをGitHubで公開)
FPGAマガジンNo.17 の 80 ページから「高位合成ツールVivado HLS 特設記事」ということで、記事を書きました。
なお、その記事中に使用したC や C++ のソースコードをGitHubで公開しました。
AXI4マスタ版ラプラシア ン・フィルタ最速の条件
この記事はFPGAマガジンNo.17 に載るはずだったけど、ページが足りなくて載せることができなかったコラムです。
Vivado HLSで stdint.h を使用する
FPGAマガジンNo16 のAXI4 Master のソースコードと、FPGAマガジン No.17 のAXI4-Stream のソースコードを公開しているが、taksei さんから「ソースコードを64bit Linux版VivadoでC-Sim実行してみたのですが、long型が8バイトとして確保されるため、BMPファイルのリード・ライトに失敗するようです。」との報告 があった。long型で4バイトのところ、8バイトになっていたようだ。
そこで、taksei さんに教えて頂いたように、stdint.h を使用して、uintX_t や intX_t を使用することにした。taksei さん、ありがとうございました。

Vivado HLS の符号付 C++の任意精度固定小数点型について
Vivado HLS の符号付 C++の任意精度固定小数点型について疑問があったので調べてみた。
Vivado HLS の C++の任意精度固定小数点型は、C++のテンプレートを使用して、ap_[u]fixed で宣言される。

Vivado HLSのCoSim がNorton Endpointの検疫に引っかかる
Vivado HLSのCoSim がNorton Endpointの検疫に引っかかってしまった。
Vivado HLS のバージョンは2017.1 だが、2016.4 も同様に引っかかっている。

Vivado HLS の任意精度固定小数点型を使用した内積の計算
今回は、配列の内積をVivado HLS の任意精度固定小数点型を使用して計算してみようと思う。浮動小数点数の計算値と比較してみよう。
Vivado HLS の浮動小数点型を使用した内積の計算
任意精度固定小数点型の比較のために作った浮動小数点数の内積の計算だが、思ったより使用リ ソースが少なかったので、書いておくことにした。

「ゼロから作るDeep Learning」の2層ニューラルネットワークのハードウェア化4(Vivado HLS)
今回は、前回作成した重みやバイアス、MNISTデータセットの一部のヘッダファイルを使用して、Vivado HLS でMNISTの手書き数字を判定するハードウェアを作る。ただし、Softmax は実装が難しいし、最大値を取れば数字は推定できるので、実装していない。
「ゼロから作るDeep Learning」の2層ニューラルネットワークのハードウェア化5(推論の検証)
前回は、Vivado HLSを使用して、MNISTデータセットで、手書き数字を認識する2層のニューラルネットワークの推論のハードウェア化を行った。今回は、前回、ハードウェア化した ニューラルネットワークは 8 の推論をミスってしまった。MNIST データの 0 個目から100 個のデータを使用して検証したので、もう少し、違ったデータで検証してみよう。
「ゼロから作るDeep Learning」の2層ニューラルネットワークのハードウェア化6(指示子を入れる)
前回は、FPGAに実装しようとしているMNISTの推論ハードウェアが本当にうまく 行っているのか?を確かめた。300個の手書き数字を認識した結果、精度は97.3 % であることが分かった。しかし、人間が判別しやすい手書き文字が必ずしもMNISTの推論ハードウェアに判別しやすいわけではないということが分かった。
今回は、実際にIP として使用できるようにVivado HLS に指示子を入れてみよう。
「ゼロから作るDeep Learning」の2層ニューラルネットワークのハードウェア化7(指示子を入れる2)
前回は、指示子を入れて、入力ポートと出力ポートを1個ずつバラバラにしてみた。今回は、実際 に使えるように指示子を入れてみよう。
インターフェースを決定しよう。入力は、AXI4 Master かAXI4-Stream だろう?AXI4 Master をやってみたが、入力ポートのビット幅が8ビットなので、32ビット幅のAXI4 バスに4個の入力データが入力されてきた。やはり、32ビット幅で1ピクセルデータとしたいということもあり、AXI4-Stream で行くことにした。
出力ポートは、最大値をハードウェアで判定して、答えの数字をバイナリで出力しても良 いのだが、10個の値をAXI4-Lite でARM プロセッサがRead して、最大値を判定することにしようと思う。そうすれば、ソフトウェアでSoftmax を取ることもできる。
「ゼロから作るDeep Learning」の2層ニューラルネットワークのハードウェア化8(浮動小数点数)
前回は、使いそうなインターフェース指示子を入れてみた。入力はAXI4-Stream で出力は、AXI4-Lite だった。今回は、内部の処理を浮動小数点数で処理することで、どのくらいリソースを消費するのか確かめてみよう。

「ゼロから作るDeep Learning」の畳み込みニューラルネットワークのハードウェア化4(Vivado HLS1)
前回は、重みやバイアスのパラメータをC の配列に出力した。今回は、畳み込みニューラルネットワークのC ソースコードを作成してVivado HLSでハードウェア化してみよう。

「ゼロから作るDeep Learning」の畳み込みニューラルネットワークのハードウェア化6(再度Vivado HLS )
前回は、畳み込み層のカーネルを10個にして畳み込みニューラルネットワークを学習させたとこ ろ、固定小数点数用に量子化した精度も 98.69 % だった。
今回は、畳み込み層のカーネルを10個にしたときの重みやバイアスを使用してVivado HLSで畳み込みニューラルネットワークを実装してみよう。
「ゼロから作るDeep Learning」の畳み込みニューラルネットワークのハードウェア化7(C/RTL協調シミュレーション)
前回は、畳み込みニューラルネットワークをVivado HLS でハードウェア化することができた。今回は、HDLコードを見たり、C/RTL協調シミュレーションをしてみてから、IP化を行ってみよう。ただし、デフォルトのインター フェースのままでは、IP にしたときに使いにくいので、実際に使用する際にはAXI バスにする。

MNISTの畳み込みニュー ラルネットワークで自分の手書き数字を認識する1
”「ゼロから作るDeep Learning」の畳み込みニューラルネットワークのハードウェア化8(性能向上を図る)”までで、「ゼロから作るDeep Learning」の畳み込みニューラルネットワークのハードウェア化は完了した。しかし、手書き数字を認識するとは言ってもMNISTの手書き数字を認識する精度が 99 % と言っても自分の手書き数字を認識できたわけではない。ということで、自分で手描きの数字を書いて認識させてみることにした。
MNISTの畳み込みニュー ラルネットワークで自分の手書き数字を認識する2
前回はお絵描きソフトのPaint.net でブラシ幅 2 のペイントブラシ・ツールを使用して書いた手書き数字を認識してみたが、認識精度はいまいちだった。今回は、GIMP2 で幅 2 ピクセルの鉛筆ツールを使用して書いた手書き数字を認識させてみようと思う。
MNISTの畳み込みニュー ラルネットワークで自分の手書き数字を認識する3(カメラ画像)
前回はGIMP2 で幅 2 ピクセルの鉛筆ツールを使用して書いた手書き数字を認識させてみた。今回は、手書き数字をカメラで撮影した画像を切り出して認識させてみよう。

手書き数字認識用畳み込み ニューラルネットワーク回路の製作2(手書き数字認識用四角枠表示回路)
前回は、カメラで撮影した画像から手書き数字を指定し、手書き数字認識用畳み込みニューラル ネットワークを使用して認識する回路の概要を解説した。今回は、そのパーツとなる手書き数字認識用四角枠表示回路をVivado HLS を使用して作ってみよう。
手書き数字認識用畳み込み ニューラルネットワーク回路の製作3(畳み込みNN)
前回は、手書き数字認識用四角枠表示回路が完成した。これで画像中に認識する四角枠を表示する ことができた。この四角枠の中に手書き数字を入れれば認識することができる。今回は、四角枠の中の手書き数字を認識する畳み込みニューラルネットワークを作成 しよう。

Bash on Windows 10にVivado WebPACK 2017.2をインストールした3(Vivado HLS)
前回は、Bash on Windows 10 の日本語表示について書いた。今回は、Bash on Windows 10 でVivado_HLSを使ってみよう。   

HLS ビデオライブラリの hls::LineBuffer のVivado HLS 2015.4 以前とその後での変更点1(メモリ・ライン・バッファー)
Vivado HLS 2016.1 から hls::LineBuffer と hls::Window のクラス・メソッドが大きく変更になった。Vivado HLS 2015.4 までは、 hls::LineBuffer と hls::Window の配列の並びは、列はインデックス 0 からなのだが、行はインデックス「行の配列の最大数」かになっていた。
HLS ビデオライブラリの hls::Window のVivado HLS 2015.4 以前とその後での変更点2(メモリ・ウインドウ・バッファー)
hls::LineBuffer と同様に、hls::Window も行のインデックスとクラス・メソッドが変更になっているので紹介する。
hls::LineBuffer と同様に、hls::Window もガボール・フィルタでカーネルとして、重みとの演算に使用されている。
HLS ビデオライブラリの hls::Window のVivado HLS 2015.4 以前とその後での変更点3(ソースコード)
今回は、ソースコードを貼っておこうと思う。Vivado HLSのソースコードはVivado HLS 2016.1 以降のメモリ・ライン・バッファーとメモリ・ウインドウ・バッファーのメソッドを使用している。それに対して、テストベンチはVivado HLS 2015.4 以前のメソッドを使用しているので、比べてみてほしい。

Vivado HLS で画像のサイズを縮小して白黒変換(resize_gray)
”1/10 まで縮小して白黒変換”ブロックをVivado HLS で作ることにする。ただし、図では”1/10 まで縮小して白黒変換”ブロックはAXI4 Master の予定だったが、性能が出せるようにDMA Read は分けようと思う。”1/10 まで縮小して白黒変換”ブロックはAXI4 Stream の入力ポートと出力ポートを持つように実装しよう。Vivado HLS の HLS ビデオライブラリの Resize() を使用して縮小することにしようと思う。
実際には1/13に縮小した。
画像をリサイズするために DMA Read IPをVivado HLSで製作した1(dmar4resize_gray)
”Vivado HLS で画像のサイズを縮小して白黒変換(resize_gray)”でAXI4 Stream 入力の画像をリサイズして白黒変換するIP (resize_gray))を作成した。今回は、フレームバッファからDMA Read して AXI4 Stream 出力して resize_gray にAXI4 Stream 入力するIP (dmar4resize_gray)を作成する。
画像をリサイズするために DMA Read IPをVivado HLSで製作した2(dmar4resize_gray)
前回は、フレームバッファからDMA Read して AXI4 Stream 出力して resize_gray にAXI4 Stream 入力するIP (dmar4resize_gray)のC シミュレーションを行った。Ubuntu 16.04 上のVivado HLS 2016.4 はC シミュレーションがうまく行かなかったが、Windows 10 Pro 上のVivado HLS 2016.4 はC シミュレーションがうまく行った。
今回は、C コードの合成、C/RTL協調シミュレーション、Export RTL を行う。
白線追従走行用畳み込み ニューラルネットワークのチューニング
”白線追従走行用畳み込みニューラルネットワークの製作18(Vivado HLSでCシミュレーション)”
”白線追従走行用畳み込みニューラルネットワークの製作19(Cコードの合成、IP化)”
で書いた straight_conv_nn2 プロジェクトの straight_conv_nn2.cpp をチューニングしてみた。C ソースコードはそのままに、指示子を挿入して、速度が出るようにやってみたが、結構いい加減に指示子を挿入している。
Vivado HLS で実装した畳み込みニューラルネットワークの指示子による性能差
Vivado HLS で実装した白線追従用の畳み込みニューラルネットワークで指示子を入れていないときと入れたときの性能差を比べてみよう。
Vivado HLS で実装した畳み込みニューラルネットワークの指示子による性能差2
前回は、指示子なしの場合の性能とリソース使用量と目いっぱい指示子を入れたときの差を検証し た。今回は更に性能が向上したのでご紹介する。
Vivado HLS で画像のサイズを縮小して白黒変換2(resize_gray)
”Vivado HLS で画像のサイズを縮小して白黒変換(resize_gray)”を少し修正した。resize_grey はOpenCV やHLS ビデオライブラリを使用して画像をリサイズして白黒変換するのだが、その色のビット・フィールドのアサインはBGR になっている。現在の自作カメラ・インターフェイス IP などのハードウェアの色ビットの割り当てはRGB になっているので、色のビット・フィールドを入れ替える必要がある。そのため、resize_gray の色ビット・フィールドをRGB に入れ替えようと思う。
AXI4 Stream版白線追従走行用畳み込みニューラルネットワークIPその1(C シミュレーション)
”白線追従走行用畳み込みニューラルネットワークの製作18(Vivado HLSでCシミュレーション)”
”白線追従走行用畳み込みニューラルネットワークの製作19(Cコードの合成、IP化)”
で作成した白線追従走行用畳み込みニューラルネットワークをAXI4 Streamで入力するように変更した。これは、”Vivado HLS で画像のサイズを縮小して白黒変換2(resize_gray)”のAXI4 Stream 入力を受けて、白線追従走行用畳み込みニューラルネットワークにそのAXI4 Stream データを入力して処理する。
AXI4 Stream版白線追従走行用畳み込みニューラルネットワークIPその2(C シミュレーション2)
”AXI4 Stream版白線追従走行用畳み込みニューラルネットワークIPその1(C シミュレーション)”は、、”Vivado HLS で画像のサイズを縮小して白黒変換2(resize_gray)”のAXI4 Stream 入力を受けてとは書いたが、BGR になってしまっていて、RGB では無かったので書き直した。また、畳み込みニューラルネットワークの最後の全結合層の出力をIP の出力として返していたが、分かりにくいので、進行方向の番号を返すように変更した。ちなみに 0 - 左旋回、1 - 直進、2 - 右旋回だ。
CNNのVivado HLS実装のstraight_conv_nn2 を再度C シミュレーション
”AXI4 Stream版白線追従走行用畳み込みニューラルネットワークIPその2(C シミュレーション2)”で 、”白線追従走行用畳み込みニューラルネットワークの製作18(Vivado HLSでCシミュレーション)”のstraight_conv_nn2 の精度が良かったのは画像が良かったからという結論が出たので、精度の悪そうな画像でもう一度、straight_conv_nn2 のC シミュレーションを行った。
CNNのVivado HLS実装のstraight_conv_nn2 の演算精度を変更する
前回は、straight_conv_nn2 の精度が良かったのは画像が良かったからという結論が出たので、精度の悪そうな画像でもう一度、straight_conv_nn2 のC シミュレーションを行った。そうすると、ハードウェアの精度は56.7 % だった。これでは精度が悪すぎるので、演算の精度、つまりビット幅を見直すことにした。演算のビット幅を変えながら誤差を見ていこう。
AXI4 Stream版白線追従走行用畳み込みニューラルネットワークIPその3(C シミュレーション、合成)
前回は、AXI4 Stream のビットアサインがBGR になってしまっていて、RGB では無かったので書き直した。また、畳み込みニューラルネットワークの最後の全結合層の出力をIP の出力として返していたが、分かりにくいので、進行方向の番号を返すように変更した。ちなみに 0 - 左旋回、1 - 直進、2 - 右旋回ということだったが、右旋回の出力が15個の内の5個間違っていた。それで、”CNNのVivado HLS実装のstraight_conv_nn2 の演算精度を変更する”で演算のビット幅を変更した。今回はどの程度右旋回のエラーが直っているか?を見てみよう。
dmar4resize_gray, resize_gray, straight_conv_nn2_axis2 をVivado HLS 2017.2 で IP化
今まで作ってきたIP のdmar4resize_gray, resize_gray, straight_conv_nn2_axis2 は今まで、Vivado HLS 2016.4 を使用してきたが、Vivado HLS 2017.2 で IP化しようと思う。やはり、ZYBOのシステムはVivado 2017.2 で構築するので、その方が良いだろうと思う。

a と b の信号を切り替えるVivado HLSのセレクタ
a と b の信号を切り替えるVivado HLSのセレクタを作った。
これだけならば、Verilog HDL で書いて、なひたふさんの記事”VivadoのIPインテグレータでRTLソースをIP化せずに、モジュールとして追加する”を参考にしてRTL のIP としてIP Integrator にインスタンスして使えばよいのだが、選択信号(select)をARM プロセッサから選択したいということでVivado HLS 2017.2 でプロジェクトを作ってやってみた。

2017年度 Zynq+Vivado HLS勉強会概要
今度、筑波大学でやる予定の「2017年度Zynq+Vivado HLS勉強会概要」です。

Vivado HLS 2015.4と2017.2の合成時の違い
Linux 版のVivado 2017.2 で乗算回路を作った。FPGAマガジンNo.14 にも書いた乗算回路のC 記述だ。この回路で、Vivado HLS 2015.4 とVivado HLS 2017.2 で合成時のリソース使用の違いを検証した。

Vivado HLS 2017.3.1 における識別子の違いによる任意精度固定小数点データ型の動作の違い1
Zynq+Vivado HLS 勉強会で使用する予定のVivado HLS 2017.3 における識別子の違いによる任意精度固定小数点データ型の動作の違いをブログに書いて置く。
Vivado HLS 2017.3.1 における識別子の違いによる任意精度固定小数点データ型の動作の違い2(合成編)
前回は、任意精度固定小数点データ型を使用した時に、量子化モードやオーバーフロー・モードの 違いによるCシミュレーションの演算結果の違いについて検討した。今回は、任意精度固定小数点データ型を使用した時に量子化モードやオーバーフロー・モードの 違いによる C コードの合成結果の違いについて検討する。なお使用するVivado HLS はUbuntu 16.04 上のVivado HLS 2017.3.1 を使用した。
Vivado HLSで#define と プラグマ指示子の使用
Vivado HLS 勉強会の乗算回路で、static const size_t を使用して PIPELINE指示子の II の値を指定する方法と、#define を使用してPIPELINE指示子(プラグマ指示子)を使用する方法だ。

Vivado HLS の合成でEstimated がTarget の制約を満たせなかったときの処置
今まで、Vivado HLS の合成でEstimated の値がTarget を満たせなかったときは、Solution メニューからSolution Settings ダイアログの Synthesis でClock Period を 短い周期にしていた。それだとタイミング制約が変更されてしまうので、Uncertainty を変更したほうが良いということだ。

Vivado HLS 2017.4 で片方が定数の場合の乗算の検討1(C シミュレーション)
畳み込みニューラルネットワークの乗算を展開するため、片方が定数の乗算のリソース使用量を少なくできる方法を探っていく。ニューラルネットワークの重みは定数なので、変 数にしておく必要はない。つまり、片方が定数ということで、乗算回路を簡単化することができるということだ。ASICでは重みが固定されてしまうので、決まり きった回路になって単一機能になってしまうが、FPGAは重みが変わったら、再コンフィギュレーションすればよいだけなので、デメリットにはならない。もし動 作中に重みを変えたいときは、パーシャル・リコンフィギュレーションすれば良いだけである。ZynqやZynqMP でARMプロセッサからパーシャル・リコンフィギュレーションできれば自分で重みを変えられるので更に良いだろう。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討2(C コードの合成1)
前回は、Vivado HLS 2017.4 で片方が定数の場合の乗算を乗算記号を使用した演算と 2 の n 乗の数に分解し、それを足し合わせることで乗算する演算との比較を C シミュレーションで行った。今回は、C コードの合成を行って、2 つの演算の比較を行う。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討3(C コードの合成2)
前回は、乗数が定数の場合の乗算のC コードの合成を行って、2 つの量子化モードとオーバーフローモードでの演算の比較を行った。今回は、片方が定数なので、乗算をシフト+加算に置き換えた演算で、2 つの量子化モードとオーバーフローモードでの演算の比較を行う。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討4(畳み込み演算1)
前回は、片方が定数のときの乗算は、片方が定数と定義して、乗算記号の * を使ったほうがリソース使用量点から言っても効率が良いということになった。今回は、乗算記号の * を使用して、畳み込みニューラルネットワークの畳み込み演算の重みを定数と置いたときの乗算を検討してみよう。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討5(畳み込み演算2)
前回は、乗算記号の * を使用して、畳み込みニューラルネットワークの畳み込み演算の重みを定数と置いたときの乗算を検討した。今回は、同様に演算をするのだが、途中の演算の小数点以下の精度を 下げてみようと思う。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討6(畳み込み演算3)
前回は、乗算記号の * を使用して、畳み込みニューラルネットワークの畳み込み演算の重みを定数と置いたときの乗算で途中の演算の小数点以下の精度を下げてやってみた。今回は、従来通りの畳み込 み演算の重みの配列を使用して、LUT にマップした演算ができないかどうか?を確かめてみた。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討7(畳み込み演算4)
前回は、従来通りの畳み込み演算の重みの配列を使用して、LUT にマップされた畳み込み演算を行うことができた。今回は、畳み込みフィルタは 2 個ある。前回はそのうちの 1 個目を使用していたので、今回は、2 個目の畳み込み演算の重みの配列を使用して違いを見てみよう。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討8(畳み込み演算5)
前回は、2 個目の畳み込み演算の重みの配列を使用して違いを確認した。今回は、2 つの畳み込み演算を並列にやってみよう。
Vivado HLS 2017.4 で片方が定数の場合の乗算の検討9(畳み込み演算6)
前回は、2 つの畳み込み演算を並列に行うようにC ソースコードを書き換えたのだが、積和演算はLUT だけを使用した演算だった。さて、なぜLUT を使った演算にしてみたかというと、畳み込みニューラルネットワークを1クロックで演算できるようにするためにはDSP48E を使用すると足りなくなるという推測に基づいていた。もう 1 クロック動作はあきらめているので、DSP48E を使用しても問題は無さそうだ。ということで、DSP48E を使用する通常の積和演算をやってみた。

Vivado HLSで関数内のBRAMを関数外から制御する1
この前、Vivado HLS 勉強会で一緒だった学生さんからVivado HLSの関数内で宣言したBRAM を外から読み書きしたいのだけど、どう書いたら良いか?という質問があったので、サンプルコードを書いてみた。
Vivado HLSで関数内のBRAMを関数外から制御する2(C++のクラスを使って書いてみた)
前回は、Vivado HLS 勉強会で一緒だった学生さんからVivado HLSの関数内で宣言したBRAM を外から読み書きしたいのだけど、どう書いたら良いか?という質問があったので、C 言語でサンプルコードを書いてみた。今回は、C++ のクラスを使って、サンプルコードを書いてみた。

Vivado HLSでのAXI4-Stream のテンプレートを作成する1
”これから作る畳み込みニューラルネットワークについての目標2”で構想したAXI4- Stream で接続する畳み込みニューラルネットワークを作成するためには、ストリームのデータ幅を拡張する必要がある。そのため、Vivado HLSでAXI4-Stream のデータ幅を拡張するテンプレートを作成してC コードの合成を行ってみよう。
Vivado HLSでのAXI4-Stream のテンプレートを作成する2
前回は、Vivado HLSでAXI4-Stream のデータ幅を拡張するテンプレートを作成して合成してみたが、テンプレートのデータに配列を使ったので、合成できなかった。今回は、データを1次元配列にしてみよう。

AXI4-Stream インターフェースの畳み込み層1(C コードの合成)
”Vivado HLSでのAXI4-Stream のテンプレートを作成する2”でAXI4-Stream インターフェースのテンプレートが決定できたので、いよいよ畳み込み層を作ってみよう。畳み込み層は今まで作ってきた画像フィルタと何ら変わるところはない。
AXI4-Stream インターフェースの畳み込み層2(C シミュレーション)
前回は、2 つの実装の畳み込み層のC ソースコードを書いて、C コードの合成を行った。今回は、テストベンチを書いたので、C シミュレーションを行った。
AXI4-Stream インターフェースの畳み込み層3(C ソースコード)
前回はAXI4-Stream 版の畳み込み層のC シミュレーションを行った。今回は、そのソースコードを貼っておく。
AXI4-Stream インターフェースの畳み込み層4(C/RTL 協調シミュレーションとExport RTL)
前回は、すべてのC ソースコードとBMP 画像ファイルを貼ったので、手元でも確認できる様になったと思う。今回は、畳み込み層のC/RTL 協調シミュレーションとExport RTLを行う。
AXI4-Stream インターフェースの畳み込み層5(出力値のヘッダファイルを出力)
前回は、C/RTL 協調シミュレーションとExport RTL を行った。今回は、次の層のデータとして、畳み込み層の出力値のC のヘッダファイルを作成するようにテストベンチを変更した。

AXI4-Stream インターフェースのReLU 1(C++ ソースコード)
AXI4-Stream インターフェースの畳み込み層に続いて、AXI4-Stream インターフェースのReLU IP を作成しよう。
AXI4-Stream インターフェースのReLU 2(CシミュレーションとCコードの合成)
前回は、C++ ソースコードを貼った。今回は、Vivado HLS 2017.4 の relu プロジェクトで C シミュレーションと C コードの合成を行う。
AXI4-Stream インターフェースのReLU 3(C/RTL協調シミュレーションとExport RTL )
前回は、ReLU プロジェクトのC シミュレーションとC コードの合成を行った。今回は、ReLU プロジェクトのC/RTL 協調シミュレーションとExport RTLを行う。

AXI4-Stream インターフェースのMax Pooling 1(ソースコード)
AXI4-Stream インターフェースのReLU に続いて、AXI4-Stream インターフェースの Max Pooling を作っていこう。
AXI4-Stream インターフェースのMax Pooling 2(Cシミュレーションと合成)
前回は、AXI4-Stream インターフェースの Max Pooling のソースコードを貼った。今回はVivado HLS 2017.4 で max_pooling プロジェクトを作成して、C シミュレーションと C コードの合成を行う。
AXI4-Stream インターフェースのMax Pooling 3(C/RTL 協調シミュレーションとExport RTL)
前回は、Vivado HLS 2017.4 で max_pooling プロジェクトを作成して、C シミュレーションと C コードの合成を行った。今回は、 max_pooling プロジェクトのC/RTL 協調シミュレーションとExport RTLを行う。

Vivado HLS のエラー内容がGUI に表示されていない時の対処方法
Vivado HLS のC コードの合成で、GUI にエラー内容が表示されずに、何のエラーで終了したのかが分からない時があって困っていた。その対処方法を書いた。

AXI4-Stream インターフェースの全結合層1(C コードや指示子による性能差1)
AXI4-Stream インターフェースの Max Pooling に続いて、AXI4-Stream インターフェースの全結合層を作っていこう。
AXI4-Stream インターフェースの全結合層2(C コードや指示子による性能差2)
前回は、AXI4-Stream インターフェースの全結合層の最初のC ソースコードを合成したときの実力を見てきた。今回は、更に指示子を入れて行くと、どの様に性能が変化するかを見ていきたい。
AXI4-Stream インターフェースの全結合層3(C コードや指示子による性能差3)
前回は、ピクセルをカウントするfor ループの内部をすべて展開して 1 クロックで実行することができた。その結果として、全結合層の処理を 84 クロックで処理することができた。しかし、リソースが500 % 以上でとてもZYBO Z7-20 に入らなかった。今回は今のスキームで現実的にZYBO Z7-20 のリソースで収まる回路を考えてみよう。
AXI4-Stream インターフェースの全結合層4(C コードや指示子による性能差4)
前回は、af1_weight[][] と dot[] をBRAM にマップしたほうが良いかな?ということになったが、II = 2 クロックとなって、性能的に少し不満があったので、この辺りをチューニングしてみよう。
AXI4-Stream インターフェースの全結合層5(C シミュレーション、C/RTL 協調シミュレーション、Export RTL )
前回で、ハードウェア化する C ソースコードは確定した。今回は、テストベンチを作成して、C シミュレーション、C/RTL 協調シミュレーション、Export RTL を実行した。


AXI4-Stream インターフェースの全結合層後のReLU 1(C ソースコード)
AXI4-Stream インターフェースの全結合層後のReLU の第1回目で、今回はC ソースコードを貼っておく。
AXI4-Stream インターフェースの全結合層後のReLU 2
前回は、AXI4-Stream インターフェースの全結合層後のReLU の C ソースコードを貼った。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行う。

AXI4-Stream インターフェースの全結合層2層目1(指示子による性能差)
AXI4-Stream インターフェースの 全結合層後のReLU の後に続いて、AXI4-Stream インターフェースの全結合層2層目を作っていこう。
AXI4-Stream インターフェースの全結合層2層目2(C シミュレーション、C/RTL 協調シミュレーション)
前回は、AXI4-Stream インターフェースの全結合層2層目のC コードの合成とExport RTLを行った。今回は、C シミュレーションとC/RTL 協調シミュレーションを行う。

AXI4-Stream インターフェースの最終出力層1(C ソースコード)
AXI4-Stream インターフェースの最終出力層を作っていく。この層は、全結合層2層目のAXI4-Stream 出力を受けて、最大値の出力の配列の値に1 をセットして、それ以外の配列の値は 0 にする。
AXI4-Stream インターフェースの最終出力層2(C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL )
前回は、AXI4-Stream インターフェースの最終出力層のC ソースコードを貼っておいた。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTLを行う。
AXI4-Stream インターフェースの最終出力層3(出力フォーマットの変更 )
前回は、AXI4-Stream インターフェースの最終出力層のC シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTLを行った。今回は、出力フォーマットを変更したので、もう一度、それらをやり直す。

AXI4-Stream インターフェースの畳み込みニューラルネットワーク1(概要説明)
いよいよ今まで作ってきたAXI4-Stream インターフェースの各層をつないで、AXI4-Stream インターフェースの畳み込みニューラルネットワークをテストしていこう。
AXI4-Stream インターフェースの畳み込みニューラルネットワーク2(C コードの合成、Export RTL)
前回は、AXI4-Stream インターフェースの各層をつないだ AXI4-Stream インターフェースの畳み込みニューラルネットワークの概要を説明した。今回は、AXI4-Stream インターフェースの畳み込みニューラルネットワークのC コードの合成と Export RTL を行った。
AXI4-Stream インターフェースの畳み込みニューラルネットワーク3(シミュレーション)
前回は、AXI4-Stream インターフェースの畳み込みニューラルネットワークのC コードの合成と Export RTL を行った。今回は、AXI4-Stream インターフェースの畳み込みニューラルネットワークの C シミュレーションと C/RTL 協調シミュレーションを行う。
AXI4-Stream インターフェースの畳み込みニューラルネットワーク4(ビット幅の変更)
前回は、AXI4-Stream インターフェースの畳み込みニューラルネットワークの C シミュレーションと C/RTL 協調シミュレーションを行った。今回は、ビット幅を変更したときの精度とリソース使用量の違いを見ていこう。
AXI4-Stream インターフェースの畳み込みニューラルネットワーク5(モードの変更)
前回は、AXI4-Stream インターフェースの畳み込みニューラルネットワークのビット幅を変更したときの変化を確認した。今回は、量子化モード、オーバーフローモードを変更した場合の精度とリソー ス使用量の違いを見ていこう。

Vivado HLSでのAXI4-Stream のテンプレートを作成する3
”Vivado HLSでのAXI4-Stream のテンプレートを作成する1”で、畳み込み層の特徴マップの個数に対応するために、データを配列にしたのだが、AXI4-Stream にするという制約ではうまくかなかった。よって、”Vivado HLSでのAXI4-Stream のテンプレートを作成する2”でデータを展開して書いたのだけれど、これでは不満が残った。たくさん特徴マップがあった時に書くのが大変だからだ。それに、特徴マップの数 を変更することが難しい。配列で書けば配列の数を書き換えると、すぐに特徴マップの数を変更することができる。
その後、AXI4-Stream で各層をつなぐのではなく、HLS ストリームで接続することにしたので、データを配列にできると思う。今日はそのテストをしてみようと思う。

HLSストリーム・インター フェースの畳み込み層1(Cソースコード、C コードの合成、Export RTL)
”Vivado HLSでのAXI4-Stream のテンプレートを作成する3”で検証した結果によると、HLS ストリームでテンプレートを作れば、特徴マップの個数分のデータを配列として、HLS ストリームに加えられることが分かったので、AXI4-Stream インターフェースの畳み込み層をHLS ストリームで書き換えてみることにした。
HLSストリーム・インター フェースの畳み込み層2(C シミュレーション、C/RTL 協調シミュレーション)
前回は、畳み込みニューラルネットワークの畳み込み層をHLS ストリームで記述することで、特徴マップを配列にしてHLS ストリームで転送するように記述することができた。それで、C コードの合成、Export RTL を行った。今回は、畳み込み層の C シミュレーション、C/RTL 協調シミュレーションを行う。
HLSストリーム・インター フェースの畳み込み層3(Windows 10 のVivado HLS 使用)
Linux 版の Vivado HLS 2017.4 では(正確にいうと SDx 2017.4 のVivado HLS )では、HLSストレーム・インターフェース版畳み込み層のC/RTL 協調シミュレーションがエラーになってしまった。そこで、Windows 10 のVivado HLS 2017.4 (こちらも SDx がインストールしたVivado HLS)で試してみようと思う。なお、ソースコードは同一のコードを使用している。
HLSストリーム・インター フェースの畳み込み層4(検証用関数conv_layer2()を追加)
”畳み込みニューラルネットワークのコードを書く時の検証方法”で、異なる実装の検証用の関数 を用意することにしたので、早速、畳み込み層で検証用関数 conv_layer2() をテストベンチに実装してみた。

HLSストリーム・インター フェースのReLU1
HLSストリームの畳み込み層に続き、HLSストリームのReLU を実装して行こう。
HLSストリーム・インター フェースのReLU2(C ソースコード)
前回は、HLSストリーム・インターフェースでReLU を作成した。今回はその C ソースコードを貼っておく。

畳み込みニューラルネット ワークのコードを書く時の検証方法
白線間走行用の畳み込みニューラルネットワーク(CNN)をVivado HLS で高位合成するために最適と思われるC ソースコードを書いたのだが、今回 Max Pooling のところでソースコードにバグがあった。
max_pooling.cpp が間違っていて、2 x 2 のウインドウでの最大値を取るはずが左上の値を取るコードになっていた。(”AXI4-Stream インターフェースのMax Pooling 1(ソースコード)”参照)
問題はどうやってソースコードが間違っているのか?を検証することだと思う。これほど間違っていても、最終的な出力では、最大 1.7 % 程度の精度の差があるだけである。

HLSストリームのマック ス・プーリング層1(C ソースコード)
HLSストリームのマックス・プーリング層をやっていこう。今回は、C ソースコードを貼っておく。
テンプレートで書いたマック ス・プーリング層2(Export RTL まで)
前回は、テンプレートで書いたマックス・プーリング層のソースコードを貼った。今回は、C シミュレーション、C コードの合成、Export RTL を行った。

テンプレートで書いた畳み込 みニューラルネットワーク1(ソースコード)
今まで作ってきたテンプレートで書いた各層をつないで、畳み込みニューラルネットワーク (CNN)を構築する。層がテンプレートで書かれているので、パラメータを入れれば簡単に?いろいろなCNN をFPGA で構成することができるはず。。。
テンプレートで書いた畳み込 みニューラルネットワーク2(C シミュレーションとC コードの合成)
前回は、テンプレートで書いた各層をつないで、畳み込みニューラルネットワーク (CNN)を構築するためのソースコードを貼った。今回は、そのソースコードを使用して、Vivado HLSのプロジェクト all_layers_template を作成して、C シミュレーションと C コードの合成を行う。
テンプレートで書いた畳み込 みニューラルネットワーク2(C/RTL協調シミュレーションとExport RTL)
前回は、テンプレートで書いた各層をつないで、畳み込みニューラルネットワーク (CNN)を構築した。そして、Vivado HLSのプロジェクト all_layers_template を作成して、C シミュレーションと C コードの合成を行った。今回は、C/RTL協調シミュレーションとExport RTL を行う。


全結合層のテンプレートの変 更
この前から畳み込みニューラルネットワーク(CNN)の層のテンプレートを作ってき た。今回、MNISTのCNN を層のテンプレートで実装したのだが、BRAMのリソース使用量をオーバーしてしまったので、BRAMを多量に使用している第1層目のチューニングを変更する必要が出てき た。そのため、全結合層のテンプレートを変更することにした。

今まで作ってきた層のテンプ レートをMNIST のCNN に適用する1(C コードの合成1)
”全結合層のテンプレートの変更”で全結合層のテンプレートを変更したが、今まで作ってきた畳 み込みニューラルネットワーク(CNN) の層のテンプレートをMNIST のCNN に適用して、お手軽に素早くCNN をFPGAに実装できるかどうか?を確かめてみた。
今まで作ってきた層のテンプ レートをMNIST のCNN に適用する2(C コードの合成2)
前回は、MNISTのCNNを以前実装したときに比べて性能は84 倍になったが、リソース使用量がPYNQボードのZynq のPL 容量をオーバーしてしまった。今回は、PYNQボードのZynq に入るようにパラメータを設定しC コードの合成を行う。
その際に使用するのが、”全結合層のテンプレートの変更”で全結合層のテンプレートに追加した OUTPUT_PIPELINE_II だ。この値を変更することにより、リソース使用量を変更することができる。
今まで作ってきた層のテンプ レートをMNIST のCNN に適用する3(Export RTL まで)
前回は、PYNQボードのZynq に入るようにパラメータを設定しC コードの合成を行った。今回は、C シミュレーション、C/RTL 協調シミュレーション、Export RTL を行う。

今年度のVivado HLSセミナ
今年度の筑波大学の学生さん向けのVivado HLSセミナは5月30日(水)からで、全10回の予定です。約2時間から3時間です。
昨年度、AXI4 Masterから急に難しくなったという意見を汲んで、初心者編6回と応用編4回の計10回にしました。

TensorFlow + Kerasを使ってみた13(Vivado HLSで実装1)
前回は、MNISTのデータの一部をC のヘッダに変換した。今回は、今ままでの重みやバイアス、そして、MNISTのデータの一部を記述した C ヘッダを使用して、”今まで作ってきた層のテンプレートをMNIST のCNN に適用する3(Export RTL まで)”のVivado HLS プロジェクトに適用してみよう。
TensorFlow + Kerasを使ってみた14(Vivado HLSで実装2)
前回は、今ままでの重みやバイアス、そして、MNISTのデータの一部を記述した C ヘッダを使用して、”今まで作ってきた層のテンプレートをMNIST のCNN に適用する3(Export RTL まで)”のVivado HLS プロジェクトに適用してみたが、C シミュレーションをした時に、ほとんどのデータがエラーになってしまった。今回は、その原因を追求して原因を突き止めた。そして、もう一度、C シミュレーションを行ったところNo Error だった。成功した。
No Errorは間違いで、C シミュレーションを行ったところ、300 個の テストデータに対して、ソフトウェアのfloat 演算は 3 個、ハードウェアの固定小数点演算は 6 個のエラーが出た。

Vivado HLS の任意精度固定小数点データ型の飽和演算
全結合層は演算自体が多いので、演算自体に飽和演算をサポートするが、畳み込み層は1回の演算数が今のところ25個なので、重みの最大値、最小値から演算の途 中の最大値を導出することができる。よって、正しい値になるような演算ビット長を推測しやすい。そのような演算ビット長で演算はするのだが、次の層に送る場合 に飽和演算をサポートするとよりリソース使用量が削減される可能性がある。そのような演算をサポートするために飽和演算をサポートしない演算の結果を飽和演算 しながら、丸めたい。

MNISTのCNN 用DMA IP 1(C シミュレーション)
MNISTのCNN 用のDMA IP を作成した。
MNISTのCNN は、ap_uint<8> のHLS ストリーム・データを入力する。よって、MNISTのCNN に手書き数字データを供給するために画像を切り取り 28 x 28 ピクセルのHLSストリーム・データを供給する mnist_square_dma IP を作成する。
MNISTのCNN 用DMA IP 2(C コードの合成、C/RTL 協調シミュレーション、Export RTL)
前回は、MNISTのCNN 用のDMA IP を作成し、C シミュレーションを行った。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTLを行った。

DMA付きテンプレートを使 用したMNISTのCNN1(C ソースコード)
MNISTのCNN 用のDMA IP を”TensorFlow + Kerasを使ってみた20(特徴マップ3個のMNIST用CNNをVivado HLSで実装)”のテンプレートを使用した特徴マップ3個のMNIST のCNN に付けた。これで、PYNQ に搭載した”手書き数字認識用畳み込みニューラルネットワーク回路の製作3(畳み込みNN)”の入出力フォーマットと同じになったので、”Kerasを使用したMNIST CNNで手書き文字認識1(以前のVivado プロジェクトをVivado 2017.4に変換)”のmnist_conv_nn10_sDMA IP と入れ替えれば、DMA 付きテンプレートを使用したMNIST のCNN を試してみることができる。
DMA付きテンプレートを使用したMNISTのCNN2(C シミュレーション1)
前回は、DMA 付きテンプレートを使用したMNIST のCNN のC ソースコードを貼った。今回は、その C ソースコードを利用してC シミュレーションをしてみよう。
DMA付きテンプレートを使 用したMNISTのCNN3(C シミュレーション2)
DMA 付きテンプレートを使用したMNIST のCNN のC シミュレーションを行った。今回は、28 x 28 ピクセルの手書き数字の真ん中のエリアの0x80 より大きいピクセル数の数で手書き数字の位置を検出するというテストベンチを土日で書いていたが、失敗した。
DMA付きテンプレートを使 用したMNISTのCNN4(Cコードの合成、Export RTL)
前回は、28 x 28 ピクセルの手書き数字の真ん中のエリアの0x80 より大きいピクセル数の数で手書き数字の位置を検出するというテストベンチを土日で書いていたが、失敗した。今回は、位置を検出するのは諦めて、C コードの合成とExport RTL を行った。

Kerasで学習した重みと バイアスを使用した白線間走行用CNNをVivado HLSで確かめる
すでに、「ゼロから作るDeep Learning」のPython コードを使用して、学習した重みとバイアスをC のヘッダファイルにしたものを使用してVivado HLSで精度を確かめたブログ記事が”カーブ、直線用白線間走行用畳み込みニューラルネットワーク11(Vivado HLS でCNN を実装)”だ。これを重みとバイアス以外は使用して、Kerasで学習した重みとバイアスのVivado HLS 2018.2 での精度を見てみよう。
Kerasで学習した重みと バイアスを使用した白線間走行用CNNをVivado HLSで確かめる2
前回は、「ゼロから作るDeep Learning」のPython コードを使用して、学習した重みとバイアスをC のヘッダファイルにしたものを使用してVivado HLSで精度を確かめたブログ記事が”カーブ、直線用白線間走行用畳み込みニューラルネットワーク11(Vivado HLS でCNN を実装)”だ。これを重みとバイアス以外は使用して、Kerasで学習した重みとバイアスのVivado HLS 2018.2 での精度を見た。今回は、C コードの合成をやってみよう。

2つのHLSストリームを同 時に入力して演算してHLSストリーム出力
2つのHLSストリームを同時に入力して演算してHLSストリーム出力したい。これは、2つの 畳み込み演算を1つにまとめる機能を持ったIPをVivado HLSで作るために必要となる。
2つのHLSストリームを同 時に入力して演算してHLSストリーム出力2
前回は、2つのHLSストリームを同時に入力して演算してHLSストリーム出力したいというこ とで、コードを書いてみたが、スタート部分がシリアライズされていた。今回は、そこも並列動作させてみよう。

Duplicate IP の製作1(ソースコード)
SqueezeNet4mnist をVivado HLSのテンプレートで実装しようと思ったときに、1つのHLSストリームを 2 つのHLSストリームに分ける Duplicate IP と 2 つのHLSストリームを 1 つのHLSストリームにする Concatenate IP が必要となる。
今回は、Duplicate IP を作ってみよう。
Duplicate IP の製作2(Vivado HLS プロジェクト)
前回は、1 つの HLS ストリームを 2 つにするDuplicate IP のソースコードを示した。今回は、そのソースコードを使用して、Vivado HLS 2018.2 のプロジェクトを作成して、IP 化まで行う。

Concatenate IP の作成1
今回は Concatenate IP をVivado HLS 2018.2 で作成してみよう。
Concatenate IP は 2 つのHLS ストリームを 1 つのHLS ストリームにマージするIP で、SqueezeNet を実装するために必要となる。
Concatenate IP の作成2
前回は、Concatenate IP のソースコードを貼った。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RLT を行う。

SqueezeNet for MNIST のVivado HLS での試行1
”SqueezeNet for MNIST 3(層の統計情報とC ヘッダ・ファイルへの出力)”で層の統計情報と重みやバイアスの C ヘッダ・ファイルを出力したので、それらを使用して、SqueezeNet for MNISTで、どのくらいのリソースが必要なのかを探ってみた。
とりあえずは、層の内の第1層目の畳み込み層、ReLU, MaxPooling の 3 つを実装してみよう。
なお、実装には、conv_layer_template.h, relu_template.h, max_pooling_template.h を使用している。
SqueezeNet for MNIST のVivado HLS での試行2
”SqueezeNet for MNIST 3(層の統計情報とC ヘッダ・ファイルへの出力)”で層の統計情報と重みやバイアスの C ヘッダ・ファイルを出力したので、それらを使用して、SqueezeNet for MNISTで、どのくらいのリソースが必要なのかを探ってみようということで、前回はソースコードを示した。今回はC コードの合成結果を示す。

SqueezeNet for MNIST のVivado HLS での試行3
前回はSqueezeNet for MNISTで、どのくらいのリソースが必要なのかを探ってみようということで、C コードの合成を行って、結果を調べた。今回は、Vivado synthesis, place and route にチェックを入れてExport RTL を行い、合成結果と比較した。

Vivado HLS でディレクトリのファイル名を取得するソフトウェアを開発
学習画像をMNISTのデータ形式に変換するのに、今回は、ファイル名が連番ではないので、すべてのファイル名を取得する必要がある。
どうするか?考えたが、ググってみると、「コンピューター:C言語講座:ディレクトリ内容の読み出し」を見つけた。このコードを元にファイル名を取得するよう に書いてみた。

Ubuntu 18.04 上でVivado HLS 2018.2 でOpenCV を使用したとき?のエラー
Ubuntu 18.04 上でVivado HLS 2018.2 を使用して(サポート外なので、エラーが出てもしかたなくはあるのですが)、OpenCV のソフトウェアを作っていたときに、C シミュレーションをすると、libpng12.so.0 が無いとエラーが出て困っていました。しかし、その解消方法もわかったので、ブログに書いておきます。

ZYBOt の白線間走行用CNNをVivado HLS 2018.2 で試しに実装した
前回は、今まで作ってきたトレーニング・ファイルやラベル・ファイル、テスト・ファイ ルやラベル・ファイルを使用して、Keras で学習させ、重みやバイアスをC ヘッダ・ファイルに出力した。今回は、その重みやバイアスのC ヘッダ・ファイルを使用してVivado HLS 2018.2 でプロジェクトを作成して、量子化ビット長を設定し、C シミュレーションとC コードの合成を行う。
ZYBOt の白線間走行用CNNをVivado HLS 2018.2 でIP化1
まずは、”Kerasで学習した重みとバイアスを使用した白線間走行用CNNをIPに する1”と”Kerasで学習した重みとバイアスを使用した白線間走行用CNNをIPにする2”を参照して、Vivado HLS 2018.2 の course_conv_nn2_axis3_k プロジェクトを作成した。
ZYBOt の白線間走行用CNNをVivado HLS 2018.2 でIP化2
前回は、DMA 付きのZYBOt の白線間走行用CNNのC シミュレーションとC コードの合成を行った。今回は、C/RTL 協調シミュレーションとExport RTL を行って、IP 化する。

Vivado HLS でDMA Readしたデータを2乗し、DMA WriteするUltra96ボード用 IP を作成
”Ultra96 で ikwzm さんのDebian9 Root File Systemを動かしてみる4”でAXI HPC port を Inner Share として使用するための設定を行った。次には、デバイスツリー・オーバーレイを試すためのPLのハードウェアを作成する。そのために今回は、Vivado HLS 2018.2 を使用して、データをDMA Read で持ってきて、2乗し、そして、DMA Writeで書き込むIP を作成しよう。

Ultra96用PMOD拡 張ボードでカメラ入力11(Vivado 2018.2のcam_test_182プロジェクト8)
前回は、動作しなかったDMA_Write_SFB を修正したVivado HLS プロジェクトで、もう一度、C シミュレーション、C コードの合成、C/RTL 強調シミュレーション、Export RTL を行った。今回は、前回生成されたIP を使用して、もう一度、カメラのデータがフレーム・バッファにDMA されるのか?を確かめてみよう。

垂直方向、水平方向が反転している画像のDMA(vhflip_dma_write)
”ZYBO Z7-20でのMNISTの実装にOV5642を使用する2”で垂直方向はフリップしたのだが、水平方向はミラー無しにした。これは、Vivado HLS でカメラ画像をDMA するIP を作成する際に性能を出すためだったのだが、最初に水平方向をミラーありにして、アドレスが減りながらDMA する場合を見ていこう。
垂直方向が反転している画像 のDMA(vflip_dma_write)
前回は、垂直方向はフリップし、水平方向をミラーありにして、アドレスが減りながらDMAを行 う方式をVivado HLS で実装して、検証した。その結果、性能が出ないことがわかった。今回は、垂直方向はフリップしているが、水平方向はミラーなしの場合のDMA を実装して性能を確認しよう。

” ARRAY_PARTITION COMPLETE has exceeded the threshold (1024)”の解決策
ニューラルネットワークの重みをBRAM じゃなくてLUT にマップしたいというときがありますが、そんな時に1024 以上の配列を array_partition complete するとザイリンクス社のフォーラムの”ARRAY_PARTITION COMPLETE has exceeded the threshold (1024)”の様に、エラーが出てしまいます。この問題の解決方法です。

カメラ画像を DisplayPortに出力する3(vflip_dma_write2 の2)
前回は、vflip_dma_write2 IP のVivado HLS 2018.3 プロジェクトを作成して、ソースコードを貼った。今回は、vflip_dma_write2 プロジェクトで、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行う。
カメラ画像を DisplayPortに出力する4(disp_dmar_aixs の1)
前回は、vflip_dma_write2 プロジェクトで、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。今回は、Read 側のDMA の disp_dmar_axis IP を作成しよう。
カメラ画像を DisplayPortに出力する5(disp_dmar_aixs の2)
前回は、Read 側のDMA の disp_dmar_axis IP のコードを貼った。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行う。

keras_compressor のモデルをVivado HLSで実装する1(model_raw.h5)
”keras_compressor を試してみる3”までで作成できた畳み込みニューラルネットワークのモデルをVivado HLS のこれまでのスキームで実装してみようと思う。
keras_compressor のモデルをVivado HLSで実装する2(model_raw.h5 畳み込み層第2層目)
前回は、ホストUbuntu 18.04 に 3 つのモデルをコピーして、まずは大きいので実装はできないと思う圧縮前のモデルのパラメータの内の畳み込み層第1層目のパラメータを見た。今回は、畳み込み層第2層目のパ ラメータを見てみよう。
keras_compressor のモデルをVivado HLSで実装する3(model_raw.h5 全結合層第1層目)
前回は、keras compressor のMNIST サンプルの model_raw.h5 の畳み込み層第2層目を解析した。今回は、全結合層の第1層目をやってみよう。
keras_compressor のモデルをVivado HLSで実装する4(model_raw.h5 全結合層第2層目)
前回は、keras compressor のMNIST サンプルの model_raw.h5 の全結合層の第1層目を解析した。今回は、全結合層の第2層目をやってみよう。

(目標)Vivado HLSで1クロック毎に結果を出力できるNNを作る1(学習編)
Vivado HLS を仕様して、1クロック毎に結果を出力できるニューラル・ネットワークを作るように努力してみよう。
今回は、Jupyter Notebook を使用して MNIST データセットを使った2層の全結合層を持ったニューラル・ネットワークの学習を行って、重みとバイアスをC のヘッダファイルとして出力してみよう。
(目標)Vivado HLSで1クロック毎に結果を出力できるNNを作る2(ソースコード)
前回は、Jupyter Notebook を使用して MNIST データセットを使った2層の全結合層を持ったニューラル・ネットワークの学習を行って、重みとバイアスをC のヘッダファイルとして出力した。今回は、その重みとバイアスのヘッダファイルを使用して、Vivado HLS でニューラル・ネットワークを構成していこう。それで、今回は完成したソースコードを貼っておく。
(目標)Vivado HLSで1クロック毎に結果を出力できるNNを作る3(Vivado HLS)
前回は、MNIST データセットを使った2層の全結合層を持ったニューラル・ネットワークを構成し、そのソースコードを貼った。今回は、Vivado HLS でC シミュレーション、C コードの合成を行っていく。
(目標)Vivado HLSで1クロック毎に結果を出力できるNNを作る4(チューンナップ1)
前回は、MNIST データセットを使った2層の全結合層を持ったニューラル・ネットワークについて、Vivado HLS でC シミュレーション、C コードの合成を行った。今回は目標の1クロック毎に結果を出力できるようにチューンナップしていこう。
結局、コードサイズが大きくなって、ランタイムが長くなって、メモリ使用量が過剰になる可能性があるというエラーが解消できなかった。残念。。。
(目標)Vivado HLSで1クロック毎に結果を出力できるNNを作る5(チューンナップ2)
MNIST データセットを使った2層の全結合層を持ったニューラル・ネットワークについて、目標の1クロック毎に結果を出力できるようにチューンナップしようとしたが、large runtime and excessive memory usage エラーになってしまった。今回は、そのエラーを回避するために 1/4 の入力数に変更して高位合成してみよう。これだと合成できた。

Vivado HLS で xfOpenCV を使用する1
久しぶりにUG902 見たところ、Vivado HLS 2018.3 では、OpenCV 対応が変更され、xfOpenCV を使用するようになっていた。これはやってみないとということでやってみたいと思う。そして他にもVivado HLS が拡張されているところがあるので、それもいずれやってみたい。
Vivado HLS で xfOpenCV を使用する2(Vivado HLS 2018.3 のGUI を使用する)
前回は、xfopencv/HLS_Use_Model/ ディレクトリにある Standalone_HLS_Example をTCL スクリプトを起動してやってみた。今回は、、xfopencv/HLS_Use_Model/ ディレクトリにあるもう一つのサンプル・デザインの AXI_Sample をVivado HLS GUI を起動してやってみようと思う。
なお、HLS_UseModel_Usage_Doc.pdf を参考にしている。
Vivado HLS で xfOpenCV を使用する3(Harris コーナー検出)
前回は、xfopencv/HLS_Use_Model/ ディレクトリにあるもう一つのサンプル・デザインの AXI_Sample をVivado HLS GUI を起動してやってみた。今回は、examples ディレクトリの harris をVivado HLS GUI でやってみようと思う。
Vivado HLS で xfOpenCV を使用する4(StereoBM)
前回は、examples ディレクトリの harris をVivado HLS GUI でやってみた。今回は、StereoBM をVivado HLS GUI でやってみたい。

Vivado HLS 2019.1 を使用してBMPファイルをC のヘッダファイルに変換する
ivado HLS 2019.1 を使用して、BMPファイルをC のヘッダファイルに変換するソフトウェアを作成した。
BMPファイルをC のヘッダファイルに変換したファイルを検証してみた
前回は、Vivado HLS 2019.1 でBMPファイルをC のヘッダファイルに変換するソフトウェアを作成した。しかし、生成されたC のヘッダファイルを見ただけでは、そこから本当にBMP 画像がふくげんできるのか?が分からない。よって、今回は、C のヘッダファイルをBMP 画像に変換するソフトウェアを作成することにした。
AXI4 Stream 出力にAXI4 Stream スイッチ付きのDMA Read IP 1
DMA Read したデータをAXI4 Stream 出力するIP を作りたいのだが、AXI4 Stream 出力は 2 つにして、そのどちらかにAXI4 Stream を出力するIP を作る。これは、Xilinx のAXI Stream スイッチを使わずに、通常の画像出力とフィルタを通った画像を切り替えるために使用する。
AXI4 Stream 出力にAXI4 Stream スイッチ付きのDMA Read IP 2
前回は、DMA Read したデータをAXI4 Stream 出力するIP で、AXI4 Stream 出力が 2 つあり、そのどちらかを sel 引数によって使用できる AXI4 Stream スイッチ付き出力を備えている IP のソースコードを貼って、C シミュレーション、C コードの合成を行った。
今回は、残りの C/RTL 協調シミュレーション、C コードの合成を行う。

Zybot のモーターの回転数と回転方向を取得する2(HDLシミュレーションにVivado HLS を使用する1)
HDL を作成したら次はHDL シミュレーションだが、HDL シミュレーションもSA, SB のタイミングを作成する回路をVivado HLS で作ったら、とっても便利なんじゃない?ということで、作ってみた。
Zybot のモーターの回転数と回転方向を取得する3(HDLシミュレーションにVivado HLS を使用する2)
HDL を作成したら次はHDL シミュレーションだが、HDL シミュレーションもSA, SB のタイミングを作成する回路をVivado HLS で作ったら、とっても便利なんじゃない?ということで、作ってみた。ということで、前回は、ソースコードをブログに貼った。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTL(IP として使うことはないのだけれど)を行う。
Zybot のモーターの回転数と回転方向を取得する3(HDLシミュレーションにVivado HLS を使用する2)
HDL を作成したら次はHDL シミュレーションだが、HDL シミュレーションもSA, SB のタイミングを作成する回路をVivado HLS で作ったら、とっても便利なんじゃない?ということで、作ってみた。ということで、前回は、ソースコードをブログに貼った。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTL(IP として使うことはないのだけれど)を行う。

Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作1
Zybot のモーター制御回路の製作はひとまずペンディングにして、今年も筑波大学でやる予定のVivado HLS 勉強会の出し物として、 AXI4 Stream 版のラプラシアンフィルタの実習用回路を作成することにした。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作2
今年も筑波大学でやる予定のVivado HLS 勉強会の出し物として、 AXI4 Stream 版のラプラシアンフィルタの実習用回路を作成することにした。ということで、前回は、Windows 10 の Vivado 2017.4 で lapfilter_axis_zybo プロジェクトを作成し、lap_filter_axis 、axis2DMA2st と DMA2axis2st IP をリポジトリに登録し、lapfilter_axis ブロック・デザインを新規作成して、IP をAdd IP して、回路を作り始めた。今回は、回路を完成させて、論理合成、インプリメンテーション、ビットストリームの生成を行った。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作3
今回は、回路を完成させて、論理合成、インプリメンテーション、ビットストリームの生成を行っ た。今回は、ハードウェアをエクスポートして、SDK を起動し、アプリケーションソフトを作成して実機確認を行って、動作した。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作4(PYNQ編1)
今年も筑波大学でやる予定のVivado HLS 勉強会の出し物として、 AXI4 Stream 版のラプラシアンフィルタの実習用回路を作成することにした。勉強会というかセミナでは、なかなか機材が揃わないのでカメラを用意することができない。よって、画像は、C のヘッダ・ファイルに変換した画像を使用してラプラシアンフィルタをかけてディスプレイに表示した。前回までは、ZYBO だったが、今回はPYNQ を使用することにする。同様に、IP を使用して、ディスプレイに表示する回路を構成し、論理合成、インプリメンテーション、ビットストリームの生成を行っていこう。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作5(PYNQ編2)
PYNQ でIP を使用して、ディスプレイに表示する回路を構成し、論理合成、インプリメンテーション、ビットストリームの生成を行ったが、インプリメンテーションしたときにタイミング違 反になり、Vivado HLS で修正を試みた。しかし、C コードの合成結果が異なるもののExport RTLのレポートに変化が無かった。やはりこれは何かがおかしいということでもう一度、やってみることにした。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作6(PYNQ編3)
前回は、PYNQ でIP を使用して、ディスプレイに表示する回路を構成し、論理合成、インプリメンテーション、ビットストリームの生成を行った。今回は、SDK でアプリケーションソフトを作成し、PYNQ の実機での動作を確認してみよう。
Vivado HLS勉強会用のラプラシアンフィルタ実習用回路の製作6(ZYBO Z7-20 編)
前回は、PYNQ の実機で動作を確認できた。今回は、ZYBO Z7-20 で同様に動作を確認する。


VGA画像をXGA画像やHD画 像に変換するdisp_dmar_axis_vga IP 1
”Ultra96 MIPI拡張ボードに接続したPcam5C の画像をDisplayPort に表示する3(fpga.binファイルの生成)”で、fpga.bin の生成まで行っておいて何なのだが、disp_dmar_axis IP がこのままではまずいことに気がついた。
DisplayPort は接続するディスプレイによって、解像度の設定が違ってしまう。XGA のディスプレイだったらXGA 解像度の画像を出して、HD 解像度だったらHD 解像度の画像をLiveVideo に入力する必要がある。その加工はカメラ画像をDMA Write する側でやっていたのだが、今回のDMA Write はFixstars Tech Blog に書いてあるそのままを使用するので、DMA Read 側でいろいろな解像度の画像にすることにしよう。つまり、disp_dmar_axis IP を作り直そう。
VGA画像をXGA画像やHD画 像に変換するdisp_dmar_axis_vga IP 2(性能が足りない)
前回は、DisplayPort は接続するディスプレイによって、解像度の設定が違ってしまう。XGA のディスプレイだったらXGA 解像度の画像を出して、HD 解像度だったらHD 解像度の画像をLiveVideo に入力する必要がある。その加工はカメラ画像をDMA Write する側でやっていたのだが、今回のDMA Write はFixstars Tech Blog に書いてあるそのままを使用するので、DMA Read 側でいろいろな解像度の画像にすることにしよう。つまり、disp_dmar_axis IP を作り直そう。ということで、ソースコードやテストベンチのコードを貼った。
今回は、C シミュレーション、C コードの合成、をやってみよう。
VGA画像をXGA画像やHD画 像に変換するdisp_dmar_axis_vga IP 3(2 種類の実装を試した)
前回は、disp_dmar_axis IP を作って、C シミュレーション、C コードの合成、C/RTL 協調シミュレーションを行ったが、C/RTL 協調シミュレーション波形から性能が足りないということが分かった。今回は、ソースコードを 2 種類書いて試してみたが、うまく行かなかった。
VGA画像をXGA画像やHD画 像に変換するdisp_dmar_axis_vga IP 4(やっと完成1)
前回は、disp_dmar_axis IP 用のソースコードを 2 種類作って試してみたが、うまく行かなかった。今回は、風呂掃除をしていた時にひらめいたdisp_dmar_axis IP の実装を試してみよう。
VGA画像をXGA画像やHD画 像に変換するdisp_dmar_axis_vga IP 5(やっと完成2)
前回は、風呂掃除をしていた時にふとひらめいた。いままで画像を拡張しない時はうまく行ってい たdisp_dmar_axis IP があるのだから、それにHLSストリーム・インターフェースで画像を拡大するIP を付けたらどうか?そして、それらを並列化したら良いのでは?というアイデアだった。ということで、ソースコードを貼った。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

Vivado HLS で 2 つの引数から DMA Read する AXI4 Master モジュールを作る1
Vivado HLS で 2 つの入力のAXI4 Master モジュールを作ってみよう。題材は平方数の和を求めるコードだ。
Vivado HLS で 2 つの引数から DMA Read する AXI4 Master モジュールを作る2
前回は、x と y の平方数の和を求める C ソースコードをいろいろとチューニングしていった。しかし、入力の x と y を同じAXI4 インターフェースから取ってくるので、どうしても x と y をRead する DMA がバーストにならないという欠点があった。今回は、AXI4 インターフェースを独立な 3 個にすることで、DMA Read がバーストするようにしてみよう。
Vivado HLS で 2 つの引数から DMA Read する AXI4 Master モジュールを作る3
前回は、AXI4 インターフェースを独立な 3 個にすることで、DMA Read がバーストするようになって、ループの中を 1 クロックで実行できるようになった。今回は、AXI4 インターフェースが 3 個あるのはもったいないので、1 個のAXI4 インターフェースでループで性能を向上させたい。
Vivado HLS で 2 つの引数から DMA Read する AXI4 Master モジュールを作る4
前回は、AXI4 インターフェースが 3 個あるのはもったいないので、1 個のAXI4 インターフェースでループで性能を向上させたい。ということで、x と y を構造体で表現したのだが、性能的には、x と y を個別に実装したときと同様の性能だった。今回は、もっと成功向上を図ろうと思う。
Vivado HLS で 2 つの引数から DMA Read する AXI4 Master モジュールを作る5
前回は、x と y を構造体で表現したコードをチューニングしたが、1 クロックで 1 出力まではチューニングすることができなかった。今回は、32 ビット幅のDMA トランザクションの中で、フィールドを自分で決めて x と y を配置する形態でチューニングをしてみよう。

Ultra96用ガボールフィル タIP の作成1
Ultra96-V2 にガボールフィルタを実装しようということで、以前、ZYBO 用に作っていたガボールフィルタIP をUltra96用に変更することにした。
Ultra96用ガボールフィル タIP の作成2
前回は、ガボールフィルタをかけるフィルタ・サイズを row と col を引数に入れて設定できるように変更したソースコード、テストベンチなどを貼った。今回は、C シミュレーション、Cコードの合成を行った。
Ultra96用ガボールフィル タIP の作成3
前回は、Ultra96 用ガボールフィルタのC シミュレーション、Cコードの合成を行った。今回は、C/RTL 協調シミュレーションとExport RTL を行う。

Ultra96用ラプラシアン フィルタIP の作成1
前回は、Ultra96 用のガボールフィルタを作成したが、今回は、Ultra96 用のエッジ検出フィルタのラプラシアンフィルタを作成しよう。
Ultra96用ラプラシアン フィルタIP の作成2
前回は、Ultra96 用のエッジ検出フィルタのラプラシアンフィルタを作成するということで、ソースコードを貼った。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行う。

Vivado HLSのバージョンによる性能差(ガボールフィルタを使用)
Vivado HLS 2017.4、Vivado HLS 2018.3、Vivado HLS 2019.1 の性能差をガボールフィルタを使って比較してみよう。
ガボールフィルタの実装では結構差が出ている。Vviado HLS は各バージョンで同じプロジェクトを使えていたが、最近はプロバティが変わっていてエラーが出ることが多くなった。この3バージョンは同じプロジェクトで使いまわすことが できなかった。各バージョンで独立のプロジェクトを必要とした。

演算に任意精度固定小数点データ 型を使用したUltra96用ガボールフィルタ1
ZYBO で使用したガボールフィルタをUltra96 に持ってきたが、C/RTL 協調シミュレーションできちんと出力が出ていたのに、Vivado でIP として使うと白一色になってしまった。(ソースコードは、”Ultra96用ガボールフィルタIP の作成1”参照)
どうしようか?と思ったが、試しに演算を任意精度固定小数点データ型でやってみたところ、 Vivado に持っていっても正常動作するようになったので、紹介する。
演算に任意精度固定小数点データ 型を使用したUltra96用ガボールフィルタ2
前回は、ガボールフィルタの演算を任意精度固定小数点データ型で実装したソースコードを示し た。今回は、C シミュレーション、C コードの合成を行った。

2つのAXI4 Stream 入力データを演算してAXI4 Stream 出力1
以前、”2つのHLSストリームを同時に入力して演算してHLSストリーム出力2”で DATAFLOW 指示子を使って、2 つのHLS Stream 入力を同時に受け取ることができた。
しかし、その方法は大げさというかソースコードが分かりにくくなるため、普通の C ソースコードで、2つのAXI4 Stream 入力からデータを受け取る方法を見つけたので、書いておく。
2つのAXI4 Stream 入力データを演算してAXI4 Stream 出力2
普通の C ソースコードで、2つのAXI4 Stream 入力からデータを受け取る方法を見つけたので、ソースコードを貼って、C シミュレーションを行った。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行う。なお、Vivado HLS 2019.1 を使用している。

Vivado HLS 2019.1 でLOOG_MERGE 指示子を使う
Adom Taylor さんの”MicroZed Chronicles: HLS Working with Loops”を見て、LOOP_MERGE 指示子を発見した。Loop を 1 つにしてくれるということで、もしかしたら、AXI4-Stream で 2 つの入力ストリームがある時の 2 つの USER 待ちループを 1 個にしてくれるんじゃないだろうか?ということでやってみた。
入出力ではうまく行かなかった。

Vivado HLS でAXI4 Lite のレジスタのHDL コードを生成しよう
レジスタを生成できるツールがあるようだが、Vivado HLS でも同様に AXI4 Lite インターフェースのレジスタを C ソースコードから生成することができる。これを使って、 AXI4 Lite インターフェースのレジスタを Verilog HDL と VHDL のソースコードとして簡単に生成することができるので紹介する。

Vivado HLS 2019.1 の tgamma 関数をテストする
Vivado HLS 2019.1 の tgamma 関数がおかしいというツィートが流れてきたので、自分でもやってみた。

HDLab で”FPGAの部屋 プレゼンツ 「 HLSハンズオンセミナー基礎編」”をやります
大学内部では院生対象にVivado HLS のセミナをしていたのですが、それを元に全面リニューアルして、一般の方を対象にHDLabさんでやることになりました。

AXI4 MasterとAXI4 Streamインターフェースがあって、AXI4 Masterにmemcpy()を使用しているVivado HLSの回路
AXI4 Master インターフェースと AXI4 Stream インターフェースを持っているVivado HLS で作成した回路でAXI4 Master に memcpy() を使用していると合成時のレポートがでないということをツィッターで聞いた。ツィッターでつぶやいていたのは、 @lp6m2 さんで、聞いていみると、Xilinx のCommunity Forums にも、”Is it possible to set internal BRAM values using AXI4 protocol in HLS IP using AXI-Stream protocol?”で質問しているそうだ。


Vivado HLS の GUI コマンド実行履歴を TCL 実行スクリプトにする
今のところ、私はほとんどVivado HLS をGUI で操作しているが、TCL スクリプトで動作させることもできる。
GUI でやった履歴を TCL スクリプトにする機能が Vivado HLS にはある。
それは、 solution? -> script.tcl だ。


テンプレートで書いた畳み込み ニューラルネットワークをRTLカーネルとしてVitisで実装する1(Vivado HLS 編 1)
以前テンプレートを使用して、パラメータを変更できる形に書いた畳み込みニューラル ネットワークをVivado HLS 2019.2 でIP にすることにした。Vitis のアクセラレーション・プラットフォームでやってみたいためだ。実はこのテンプレートを使用して、パラメータを変更できる形に書いた畳み込みニューラルネットワークを Vitis のアクセラレーション・プロジェクトとして作成したところ、ビルドが通らなかったので、Vivado HLS でIP 化した後で、Vitis のRTL カーネルとして使ってみたいということだ。
Vivado HLS でIP 化すると、チューニングもしやすいし、C/RTL 協調シミュレーションで波形も確認できるのでとても良い。そこで、IP 化したVerilog HDL コードをRTL カーネルとしてVitis で使いたいと考えたわけだ。。。
今回は、Vitis のRTL カーネルと実装するためのC++ のソースコードテストベンチを貼っておく。
テンプレートで書いた畳み込み ニューラルネットワークをRTLカーネルとしてVitisで実装する2(Vivado HLS 編 2)
前回は、Vitis のRTL カーネルとして実装するためのC++ のソースコードテストベンチを貼った。今回は、そのコードをVivado HLS 2019.2 でプロジェクトを作成して実装していこう。
テンプレートで書いた畳み込み ニューラルネットワークをRTLカーネルとしてVitisで実装する3(Vivado HLS 編 3)
”テンプレートで書いた畳み込みニューラルネットワークをRTLカーネルとして Vitisで実装する1(Vivado HLS 編 1)”に Vitis のRTL カーネルを作成するためにパラメータを変更できる形に書いた畳み込みニューラルネットワークをVivado HLS 2019.2 でIP にするためのソースコードとテストベンチコードを書いたが、任意精度固定データ型をそのまま int32_t にキャストしてしまったので、小数点以下の桁が無くなってしまった。それを修正するために、任意精度固定データ型の整数ビット長を 8 ビット延長して 256 倍することにした。

ラプラシアン・フィルタを RTLカーネルとしてVitisで実装する1
テンプレートで書いた畳み込みニューラルネットワークをRTLカーネルとして Vitisで実装しようとしていたが、ソースコードとやり方が全くやったこと無いのはやり方が間違っているかコードが間違っているのか分からないので、ト ラブった時に大変だと考えた。そこで、”Vitis 2019.2 アプリケーション・プロジェクト ラプラシアン・フィルタAXI4-Streamバージョン2”で使用したラプラシアン・フィルタだったら、カーネル・アプリケーションはできているので、これを RTL カーネルとして実装することにした。
今回は、Vitis でアクセラレーション・アプリケーション・プロジェクトを作成し、ビルドした後で、Ultra96-V2 上で動作を確認した。

Vivado HLS の Vitis Bottom Up Flow を使用する1
”テンプレートで書いた畳み込みニューラルネットワークをRTLカーネルとして Vitisで実装する3(出力をグローバル・バッファからホストにコピーできない)”で all_layers_dnn が 2 個の出力バッファを使用しているので、その場合は、ホスト・メモリにコピーできないのか?を確かめるために Vivado HLS プロジェクトの square_cubed プロジェクトを作成して確かめてみよう。ついでに、Vivado HLS の新規プロジェクトを作成する時に Vitis Bottom Up Flow というチェックボックスがあるのを覚えていたので、それを使用して、Vitis の RTL カーネルを生成してみようと思う。
Vivado HLS の Vitis Bottom Up Flow を使用する2
前回は、 2 個の出力バッファを使用している時に、ホスト・メモリにコピーできないのか?を確かめるために Vivado HLS プロジェクトの square_cubed プロジェクトを作成して確かめてみようということで、 Vivado HLS 2019.2 で square_cubed プロジェクトを作成した。(Vitis 2019.2 の RTL カーネルを作成するため)
今回は、Vitis 2019.2 のアクセラレーション・プロジェクト用のVivado HLS 2019.2 プロジェクトの square_cubed プロジェクトで xo ファイルを作成しよう。

Vivado HLS 2019.2 で krnl_dma_read を作成する1(ソースコードの表示)
ストーミング接続用のhls::stream の定義は、hls::stream<ap_axiu<32,0,0,0> > にする必要がある。こうするとサイドチャネルの信号は last と keep , strb だけになる。この内の last を使用して、フレームの最後をマークしよう。
Vivado HLS 2019.2 で krnl_dma_read を作成する2(IP 化)
前回は、Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続してみようということで、最初にDMA Read を作ることにした。そして、ソースコードを貼った。今回は、それらのソースコードを使用して、Vivado HLS 2019.2 で C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

square root を Vivado HLS で実装する1
square root を Vivado HLS で実装しようと思う。厳密な square root ではなく、結果が 8 ビットの整数で表されればよい。つまり、 Sobel フィルタを実装したいので、x と y を 2 乗して足して、square Root したいので、RGB の値の範囲で square root できれば十分なのだ。
square root を Vivado HLS で実装する2
square root を Vivado HLS で実装しようということで、逐次比較型ADコンバータのやり方を真似したsquare root を求めるソースコードを作って、前回貼った。そして、テストベンチのソースコードも貼って、C シミュレーションを行った。
今回は、C コードの合成を行って、Export RTL で Vivado のインプリメンテーションの結果を見てみよう。
square root を Vivado HLS で実装する3
前回は、square root を Vivado HLS で実装しようということで、逐次比較型ADコンバータのやり方を真似したsquare root を求めるソースコードを作って、C コードの合成とExport RTL を行った。しかし、使い物にならないということが分かった。前回までの square root ソースコードは、square root するビット長を可変にしていた。しかし、実際は、Sobel フィルタで使用するので、高々、結果が 8 ビット長なので、ビット長を 8 ビットに決め打ちにした。Vivado HLS もループ長を固定値にしたほうが最適化しやすいので、これでやってみよう。

Vivado HLS 2019.2 で krnl_dma_read を作成する1(ソースコードの表示)
ストーミング接続用のhls::stream の定義は、hls::stream<ap_axiu<32,0,0,0> > にする必要がある。こうするとサイドチャネルの信号は last と keep , strb だけになる。この内の last を使用して、フレームの最後をマークしよう。
Vivado HLS 2019.2 で krnl_dma_read を作成する2(IP 化)
前回は、Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続してみようということで、最初にDMA Read を作ることにした。そして、ソースコードを貼った。今回は、それらのソースコードを使用して、Vivado HLS 2019.2 で C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。
Vivado HLS 2019.2 で krnl_dma_read を作成する3(DMA Read サイズを固定する)
”Vivado HLS 2019.2 で krnl_dma_write を作成する3”でDMA Write のサイズを固定したところ、劇的にリソース使用量が減少した。そうしたら、krnl_dma_read も同様ではないか?と思って、DMA Read サイズを固定したバージョンを作成してみることにした。

Vivado HLS 2019.2 で krnl_lap_filter を作成する1(ソースコードの表示)
Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続してみよう。
今回は、ラプラシアン・フィルタ・カーネル krnl_lap_filter を作成する。
Vivado HLS 2019.2 で krnl_lap_filter を作成する2(IP化)
前回は、ラプラシアン・フィルタ・カーネル krnl_lap_filter を作成するということで、ソースコードを貼った。今回は、Vivado HLS 2019.2 のプロジェクトを作成して、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行っていこう。

Vivado HLS 2019.2 で krnl_dma_write を作成する1
Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続してみよう。
今回は、DMA Write カーネルを作成しよう。
Vivado HLS 2019.2 で krnl_dma_write を作成する2
Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続するために、前回は DMA Write カーネルを作成したのだが、リソースを消費すぎているのが分かった。今回は、リソース使用量を少なくするように努力してみよう。
Vivado HLS 2019.2 で krnl_dma_write を作成する3
Vitis のカーネル間ストーミング接続をテストするために DMA Read カーネル ー ラプラシアン・フィルタ・カーネル ー DMA Write カーネルをストーミング接続するためのDMA Write カーネルを作成したが、リソースを消費すぎていた。リソース消費を抑えようと for ループ内のPIPELINE 指示子を削除した。そうすると C コードの合成では、リソース使用量が減った様にレポートされたが、Export RTL したらリソース使用量が急激に増えてしまった。結局うまく行かなかった。その後の解析で、どうやら除算をしているようで、それがリソース使用量の大半を占めていることが分 かった。
考えてみれば、DMA 数を設定できるということは、バーストの数を数えて行く必要がある、ということで除算を使用しているのだと思う。(私ならば減算していくが。。。)そこで、予めDMA 数をコンパイラが数えられるように定数にすれば、コンパイラが静的に解析できるはずだ。今回は X_SIZE と Y_SIZE を定数として与えてみよう。

Vivado HLS 2019.2 で xfOpenCV を使用する1(dilation 1)
Vivado HLS 2019.2 で xfOpenCV を使ってみることにした。どのくらい使えるのだろうか?
前回、Vivado HLS 2018.3 でも同様に dilation をやっている。
Vivado HLS 2019.2 で xfOpenCV を使用する2(dilation 2)
前回は、Vivado HLS 2019.2 で xfOpenCV を使ってみることにしたということで、xfopencv/HLS_Use_Model/Standalone_HLS_AXI_Example のスクリプトを実行して、 dilation_project を作成し、C シミュレーションの結果を表示した。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

Vivado HLS 2019.2 で xfOpenCV を使用する3(sobel filter 1)
前回は、xfOpenCV の dillation をやったが、今回は、xfOpenCV の xfopencv/examples/sobelfilter をやってみようと思う。ただし、この soblefilter は xf::Mat のインターフェースなので、 AXI4-Stream インターフェースに変更した。更に現状の解像度では、Ultra96 のリソースに入らないので、画像のサイズを縮小した。
Vivado HLS 2019.2 で xfOpenCV を使用する4(sobel filter 2)(xfOpenCV を使用する時のVivado HLSの設定方法)
前回は、xfOpenCV の xfopencv/examples/sobelfilter をやってみようと思う。ただし、この soblefilter は xf::Mat のインターフェースなので、 AXI4-Stream インターフェースに変更した。更に現状の解像度では、Ultra96 のリソースに入らないので、画像のサイズを縮小した。今回は、sobel_filter プロジェクトを使用して、 xfOpenCV を使用する時の GUI 上での Vivado HLSの設定方法を紹介する。
Vivado HLS 2019.2 で xfOpenCV を使用する5(sobel filter 3)
前回は、sobel_filter プロジェクトを使用して、 xfOpenCV を使用する時の GUI 上での Vivado HLSの設定方法を紹介した。今回は、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。Export RTLはエラーになった。

Vivado HLS 2019.2 で HLS Video Library を使用した Sobel フィルタを作る1
前回まで、xfOpenCV で Sobel フィルタを実装してきたが、Vivado HLS には旧 OpenCV のスキームがまだ、 2019.2 でも備わっている。それが HLS Video Library だ。Xilinx Wiki に HLS Video Library の資料がある。
HLS Video Library の hls::Sobel() を使って、Sobel フィルタを実装してみよう。
Vivado HLS 2019.2 で HLS Video Library を使用した Sobel フィルタを作る2
前回は、 HLS Video Library で実装した Sobel フィルタのソースコードを貼って、Vivado HLS 2019.2 の sobel_filter プロジェクトを示した。今回は、 sobel_filter プロジェクトで、C シミュレーション、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

Vivado HLS 2019.2 で普通に C ソースコードを書いて Sobel フィルタを実装する1
xfOpenCV 、 HLS Video Library で Sobel フィルタを実装してきたが、 C のソースコードで Sobel フィルタを実装してみよう。
なお、この Sobel フィルタの実装は、HDLab さんで、”FPGAの部屋 プレゼンツ 「 HLSハンズオンセミナー基礎編」”をやっているが、その次のセミナとして Vivado HLS のチューニング方法を詳しく解説する応用編で使用しようと思っている。ただし、ここに載せたソースコードは少し変更してある。
この Sobel フィルタの実装は、横方向と縦方向の Sobel フィルタを同時に行って、その結果を二乗和平方根を取っている。
Vivado HLS 2019.2 で普通に C ソースコードを書いて Sobel フィルタを実装する2
前回は、ivado HLS 2019.2 で普通に C ソースコードを書いて Sobel フィルタを実装するためのソースコードとテストベンチを貼った。今回は、C シミュレーション、 C コードの合成、 C/RTL 協調シミュレーション、 Export RTL を行った。

Vivado HLS 2019.2 で xfOpenCV を使用する6(resize 1)
前回は、sobel_filter をやってみたが、今回は、resize をやってみよう。 xfOpenCV の examples/resize を使用しているが、sobel_filter と同様に、AXI4-Stream 入出力に変更するために xf_resize.cpp を追加してある。
Vivado HLS 2019.2 で xfOpenCV を使用する7(resize 2)
前回は、resize をやってみようということで、 xfOpenCV の examples/resize を使用しているが、sobel_filter と同様に、AXI4-Stream 入出力に変更するために xf_resize.cpp を追加した。そのソースコードを貼って、Vivado 2019.2 のプロジェクトを生成した。
今回は、resize の C シミュレーションを行った。
Vivado HLS 2019.2 で xfOpenCV を使用する8(resize 3)
前回は、resize の C シミュレーションを行った。 800 x 600 ピクセルの画像を 60 x 45 ピクセルに変換した時は、本当に画像が薄くなってしまった。80 x 60 ピクセルの画像に変換した時も 60 x 45 ピクセルよりは濃くなったが、やはり薄かった。ユーザーズガイドを見たところ、縮小は 1/4 までだったので、200 x 150 ピクセルの画像に変更したところ、正常に縮小することができた。
今回は、200 x 150 ピクセルに縮小する場合の C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

Vivado HLS 2019.2 の HLS Video Library を使用して resize() を実装する1
”Vivado HLS 2019.2 で xfOpenCV を使用する8(resize 3)”で xfOpenCV を使用して、Vivado HLS 2019.2 で画像のサイズ変換を実装した。今回は、HLS Video Library を使用して、Vivado HLS 2019.2 で画像のサイズ変換を実装する。ソースコードを貼った。

Vivado HLS で C シミュレーションが通らずに C コードの合成で ERROR: [HLS 200-101] 'add_files': が出る場合の対処
新しく VIvado HLS 2019.2 のプロジェクトを作って C シミュレーションや C コードの合成を行ったのだが、ソースコードは間違っていないはずなのにどうしてもエラーになってしまう。環境を捨ててしまって、実際のエラーを貼れないのが残念だ。

Vivado HLS 2019.2 の HLS Video Library を使用して resize() を実装する2
前回、カラーの画像をカラーで縮小する HLS Video Library の resize のソースコードを貼ったが、”Vivado HLS 2019.2 で xfOpenCV を使用する6(resize 1)”でも、カラーの画像を白黒画像に縮小する resize だったので、今回は、同様に、カラーの画像を白黒画像に縮小する resize のソースコードを貼った。
Vivado HLS 2019.2 の HLS Video Library を使用して resize() を実装する3
前回は、カラー画像の resize をカラー画像から白黒画像への resize に変更した。今回は、いろいろな縮小率で画像が縮小できるか?を C シミュレーションで検証した。
Vivado HLS 2019.2 の HLS Video Library を使用して resize() を実装する4
前回は、HLS Video Library の resize を使用して、800 x 600 ピクセルの画像を 60 x 45 ピクセル、100 x 75 ピクセル、200 x 150 ピクセルに縮小できるかどうか?を C シミュレーションですべてできることを確認した。今回は、60 x 45 ピクセル、200 x 150 ピクセルに縮小した時の C コードの合成、 C/RTL 協調シミュレーション、 Export RTL を行った。

Vivado HLS 2019.2 で xfOpenCV の medianblur をやってみる1
もう1つ xfOpenCV をやってみようということで、日曜日の朝に AXI4-Stream 版の medianblur を作って、C シミュレーション、C コードの合成までできていたはずだったが、日曜日の夕方にカラー画像だったので、白黒画像でやってみようと思ったら AXI4-Stream から Mat 変換で empty だと言われて止まらなくなった。カラー画像対応に戻しても同様に C シミュレーションが動かなくなった。まだ修復できていないので、medianblur の Mat 画像版というか、xfOpenCV の medianblur サンプルそのままをやってみよう。
Vivado HLS 2019.2 で xfOpenCV の medianblur をやってみる2
前回は、medianblur の Mat 画像版というか、xfOpenCV の medianblur サンプルそのままをやってみようということで、C シミュレーションを行って、ノイズ除去することができた。今回は、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

Vivado HLS 2019.2 で xfOpenCV のAXI4-Stream 版 medianblur をやってみる1
”Vivado HLS 2019.2 で xfOpenCV の medianblur をやってみる1”で動いていた AXI4-Stream 版 medianblur が動かなくなったと書いたが、これは、画像の大きさを指定するところで、height と width を取り違えていたからだった。4k2k 画像から HD 画像に変更しようとして、height と width を間違ってしまっていたのだった。orz
新たに作り直したAXI4-Steram 版の medianblur を紹介する。だいぶ自分の書き方になってきたのだが、xf_headers.h は Xilinx 社のソースコードをそのまま使用している。
なお、白黒画像とカラー画像を define で切り替えるようにしてある。
Vivado HLS 2019.2 で xfOpenCV のAXI4-Stream 版 medianblur をやってみる2
前回は、新たに作り直したAXI4-Steram 版の medianblur のソースコードを貼った。今回は、カラー画像出力と白黒画像出力の C シミュレーションを行った。
Vivado HLS 2019.2 で xfOpenCV のAXI4-Stream 版 medianblur をやってみる3
前回は、カラー画像出力と白黒画像出力の C シミュレーションを行って、成功した。今回は、カラー画像出力と白黒画像出力それぞれにおいて、C コードの合成、C/RTL 協調シミュレーション、Export RTL を行った。

2020年度版Vivado HLSセミナ資料の項目
2020年度版Vivado HLSセミナ資料の項目です。
筑波大学で院生対象にやりたいと思っていますが、新型コロナウィルス対応でどうなるか、分かりません。遠隔になるかも?
バージョン2017.4 からバージョン 2019.2 に変更しました。また最後に Vivado HLS の xfOpenCV 対応方法の演習を追加しました。2019.2 なのでアプリケーション・ソフトの作成には Vitis を使っています。
総スライド数は xfOpenCV のVivado 部分を除いて(まだ書いてません) 1,320 枚くらいです。

Vivado HLS 2019.2 の Encoding の設定機能
Vivado HLS 2019.2 から Encoding 設定機能が付ていたので、その機能を確認してみよう。

Windows 10 の Vivado HLS 2019.2 で mnist_nn プロジェクトを C シミュレーションしたときのエラー
Windows 10 の Vivado HLS 2019.2 で mnist_nn プロジェクトを C シミュレーションしたときに謎のエラーが発生する。トラブルシューティングしてみたので、その顛末を書いておく。

Vivado HLS 2020.1 vs Vitis HLS 2020.1 (プロジェクトの作成)
現在、Vivado HLS のセミナを大学で、hdlab さんでは、一般向けの Vivado HLS セミナを行っている。(ちなみに、この 2 つは内容が違います)
しかし、いずれは Vitis HLS に移行する必要があると思う。よって、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。なお、使用している OS は Ubuntu 18.04 だ。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 (C シミュレーション、C コードの合成)
Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は、プロジェクトの作成までの違いを探っていたが、あまり違いは見られなかった。今回は、C シミュレーションと C コードの合成をやってみよう。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その3 (C/RTL 協調シミュレーション、Export RTL)
簡単な乗算回路で、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は C シミュレーションと C コードの合成をやってみることにした。今回は、 C/RTL 協調シミュレーションと Export RTL をやっていこう。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その4 (AXI4 Lite インターフェースの Slave 機能)
簡単な乗算回路で、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は C/RTL 協調シミュレーションと Export RTL を比較した。今回は、AXI4 Lite インターフェースの Slave 機能を比較してみよう。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その4 (AXI4 Lite インターフェースの Slave 機能)の動作を確認する
簡単な乗算回路で、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較するということで、前回は、AXI4 Lite インターフェースの Slave 機能で比較したのだったが、Export RTL の機能で、リソース使用量が DSP 1 個のみになってしまった。Vivado HLS 2019.2 で同様にやってみたが、FF や LUT を使っていた。そこで、今回は 前回、Vitis HLS 2020.1 で作成した 乗算 IP を使用して、Vivado で回路を作成し、動作させてみた。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その5 (AXI4 インターフェースの Master 機能1)
前回は、AXI4 インターフェースの Slave 機能の簡単な乗算回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較した。今回は、AXI4 インターフェースの Master 機能の 2 乗回路を使用して、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。今回の行うのは C シミュレーションと C コードの合成だ。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その6 (AXI4 インターフェースの Master 機能2)
AXI4 インターフェースの Master 機能の 2 乗回路を使用して、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。
前回は、 C シミュレーションと C コードの合成を行った。今回は、C/RTL 協調シミュレーションと Export RTL を行う。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その7 (AXI4-Stream インターフェース 1)
前回は、AXI4 インターフェースの Master 機能の 2 乗回路を使用して、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する、ということで、、C/RTL 協調シミュレーションと Export RTL を行った。今回は、AXI4-Stream インターフェース機能の 2 乗回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。今回は、 C シミュレーションと C コードの合成を行う。
Vivado HLS 2020.1 vs Vitis HLS 2020.1 その8 (AXI4-Stream インターフェース 2)
XI4-Stream インターフェース機能の 2 乗回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較するということで、前回は、C シミュレーションと C コードの合成を行った。今回は、C/RTL 協調シミュレーションと Export RTL を行う。

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった1(Vivado HLS 編 1)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにする。mnist_nn プロジェクトでの不具合。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった2(Vivado HLS 編 2)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、Vivado HLS プロジェクトを作成し、C シミュレーションを行った。今回は、C コードの合成、C/RTL協調シミュレーション、Export RTL を行った。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった3(Vivado 編)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は Vivado HLS の C/RTL 協調シミュレーションを行って正常動作することを確認し、Export RTL で IP 化を行った。今回は、 Vivado 2019.2 を使用して、ブロックデザインを作成し、論理合成、インプリメンテーション、ビットストリームの生成を行い、XSA ファイルを作成した。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった4(Vitis 編)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は Vivado 2019.2 を使用して、ブロックデザインを作成し、論理合成、インプリメンテーション、ビットストリームの生成を行い、XSA ファイルを作成した。今回は、その XSA ファイルを使用して Vitis 2019.2 のプラットフォームを作成し、アプリケーション・プロジェクトを作成して、実機で検証する。
どうやら、0x48C00018 番地に書けないようだ。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった5(デバック編 1)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、 XSA ファイルを使用して Vitis 2019.2 のプラットフォームを作成し、アプリケーション・プロジェクトを作成して、実機で検証したが動作しなかった。今回は Vivado Analyzer を挿入して AXI インターフェースのアクセスがあるかどうか?を調べてみよう。
processing_system7_0_M_AXI_GP0 からのアクセスが来ないようだ?
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった6(デバック編 2)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、Vivado Analyzer を挿入して AXI-Lite インターフェースのアクセスがあるかどうか?を調べたが、アクセスは無かった。今回は、この構成でAXI-Lite インターフェースのアクセスがあるか?を調べるために DMA_pow2 IP (2乗 IP)を Add IP してアクセスを調べてみる。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった7(デバック編 3)
Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、Vivado Analyzer を挿入して AXI-Lite インターフェースのアクセスがあるかどうか?を調べたが、NN IP のアクセスは無かった。前回は、この構成でAXI-Lite インターフェースのアクセスがあるか?を調べるために DMA_pow2 IP (2乗 IP)を Add IP してアクセスを調べたところ、問題なくアクセスが来ていた。今回は、NN IP でもアクセスが来るようになったので、その顛末を書いておく。
やはり、プログラムが多すぎるのが行けないのか?
配列もローカル変数で取っているが、スタックに配置されると思うので、大きな配列を取るのはまずいだろうか? malloc() でヒープに取ってみよう。
Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった8(動作しました)
Vivado HLS 2019.2 でニューラルネットワーク(NN)の IP を作成し、Vivado で IP を使用して回路を作成したが、動作しないという問題があった。これは、NN IP への AXI4-Lite インターフェースのトランザクションが出ていなかったが、”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった7(デバック編 3)”で、main() 関数のソフトウェアによるニューラルネットワークを計算する部分を削除すると、NN IP への AXI4-Lite インターフェースのトランザクションが出るようになった。そこで、”Vitis のデフォルトの Stack size, Heap size は 8k バイトだった”で、スタックサイズを 128 k バイトに拡大すると、main() 関数のソフトウェアによるニューラルネットワークを計算する部分を削除しなくても AXI4-Lite インターフェースのトランザクションが出るようになった。Run すると正常な出力が出た。完成だ。結局 script.ld のスタック容量が足りないのが原因だったようだ。心配していたバイトレーンのエンディアンの影響も無かった。

Vivado HLS で AXI4 Master を使用したときのビット幅1(128 ビットの例)
Vivado HLS で AXI4 Master を使用したときに、32ビット幅以外の時はどのような実装になるかを調べてみた。
使用するプロジェクトは DMA_pow2_XX プロジェクトだ。
これは、AXI4 Master にする引数を ap_int で書いてあって、いろいろなデータ幅にすることができる。
Vivado HLS で AXI4 Master を使用したときのビット幅2(いろいろなビット幅)
Vivado HLS で AXI4 Master を使用したときに、32ビット幅以外の時はどのような実装になるかを調べてみたということで、前回は、128 ビット幅の例を試してみた。今回は、いろいろなビット幅を試してみよう。

Vivado HLS の任意精度固定小数点データ型 ap_fixed 型にソフトウェアから直接データを入力するには?
”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった1(Vivado HLS 編 1)”の Vivado HLS 2019.2 でハードウェアにする ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> in[784] の AXI4 Master のポートに入力するデータを”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった8(動作しました)”で、uint8_t で定義された配列から入力した。
これは、任意精度固定小数点データ型の方が、2 新数の小数点位置を変更したものだったからだ。つまり、ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> は uint8_t の小数点位置を 8 ビット左に移動したものだ。つまり、uint8_t の 0x01 は ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> では、0.00390625 となる。そこで、 ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> in[784] の AXI4 Master のポートに入力するデータを用意する場合は、uint8_t の配列を渡せばよい。uint8_t が 1/256 倍になっているのだが。。。
どうして、こういうことをするかというと、ソフトウェアには ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> データ型が無いから、この型を使えないからだ。

それでは、符号なしの場合はこれで良いが、符号ありの場合の int8_t でデータを渡すための ap_fixed の型は何だろう?ということでやってみた。
それは、ap_fixed<8, 1, AP_TRN_ZERO, AP_SAT> だった。なお、ここでは、 AP_TRN_ZERO, AP_SAT は意味がない。 8, 1 が重要だ。

Vivado HLS, Vitis HLS で 2022 年問題発生
”Microsoft Exchange Server、日付チェック問題でメール配信停止(対処中)”だそうですが、Vivado HLS, Vitis HLS も 2022 年問題で現在、Export RTL ができなくなっています。
Vivado HLS, Vitis HLS の 2022 年問題にパッチを当てる
”Vivado HLSリビジョンオーバーフロー問題のパッチの当て方”(参考にさせて頂きます)を見て Vivado HLS, Vitis HLS の 2022 年問題のパッチが出ていることに気がついたので、私もやってみることにした。



inserted by FC2 system