FC2カウンター FPGAの部屋 AXI4-Stream インターフェースの畳み込み層2(C シミュレーション)
FC2ブログ

FPGAやCPLDの話題やFPGA用のツールの話題などです。 マニアックです。 日記も書きます。

FPGAの部屋

FPGAの部屋の有用と思われるコンテンツのまとめサイトを作りました。Xilinx ISEの初心者の方には、FPGAリテラシーおよびチュートリアルのページをお勧めいたします。

AXI4-Stream インターフェースの畳み込み層2(C シミュレーション)

AXI4-Stream インターフェースの畳み込み層1(C コードの合成)”の続き。

前回は、2 つの実装の畳み込み層のC ソースコードを書いて、C コードの合成を行った。今回は、テストベンチを書いたので、C シミュレーションを行った。

まずは、ハードウェア化する C ソースコードとして、hls::LineBuffer, hls::Window を使用した conv_layer.cpp を使用した。これは意味はないが、たまたまこのコードだっただけの話だ。
さて、テストベンチは、straight_RED_rect0_00_rgb.bmp という白線の白黒画像を読み込んで、畳み込みを行う。straight_RED_rect0_00_rgb.bmp は straight_RED_rect0_00.bmp のグレースケールのBMP 画像をRGB に変更した画像で、サイズは 56 x 10 ピクセルだ。
straight_RED_rect0_00_rgb.bmp を示す。
conv_layer_11_180215.png

テストベンチは、ハードウェア化する畳み込みを行う関数とソフトウェアで float 型で演算する畳み込みを行う関数を 2 つ呼び出して、その2 つの結果を比較し、その結果を出力する。そして、ある一定以上の違いがあったらエラーを出す。
次に、ハードウェアとソフトウェアの畳み込みを行う2 つの関数の出力を適当に処理して、BMP 画像にする。ハードウェアの畳み込みを行う関数のデータから出力したBMP 画像が temp_conv0.bmp と temp_conv1.bmp だ。そして、ソフトウェアの畳み込みを行う関数のデータから出力したBMP 画像が temp_conv_float0.bmp と temp_conv_float1.bmp になる。どちらも、 2 個のカーネルがあるため、2 つの画像を出力している。個の画像のサイズは、5x5 のカーネルを使用して、パッデング 0 、ストライド 1 なので、縦横とも 4 ピクセル減少して、52 x 6 ピクセルになっている。
さて、現在のVivado HLS 2017.4 の conv_layer プロジェクトを示す。
conv_layer_5_180215.png

これで C シミュレーションを行った。結果を示す。
conv_layer_6_180215.png

INFO: [SIM 2] *************** CSIM start ***************
INFO: [SIM 4] CSIM will launch GCC as the compiler.
Compiling ../../../conv_layer_tb.cpp in debug mode
Compiling ../../../conv_layer.cpp in debug mode
Generating csim.exe

outs
HW and SW results i = 0, j = 0, HW = 4.335938, -0.017578, SW = 2.956438, -0.043737
HW and SW results i = 1, j = 0, HW = 4.266602, -0.016602, SW = 2.887825, -0.041697
HW and SW results i = 2, j = 0, HW = 4.193359, -0.016602, SW = 2.813908, -0.042108
HW and SW results i = 3, j = 0, HW = 4.140625, -0.016602, SW = 2.762030, -0.041928
HW and SW results i = 4, j = 0, HW = 4.064453, -0.015625, SW = 2.685595, -0.039677
HW and SW results i = 5, j = 0, HW = 4.011719, -0.014648, SW = 2.633010, -0.038917
HW and SW results i = 6, j = 0, HW = 3.991211, -0.014648, SW = 2.612745, -0.038658
HW and SW results i = 7, j = 0, HW = 4.005859, -0.013672, SW = 2.628183, -0.038179
HW and SW results i = 8, j = 0, HW = 4.014648, -0.013672, SW = 2.636920, -0.037909
HW and SW results i = 9, j = 0, HW = 4.036133, -0.013672, SW = 2.658426, -0.037599
HW and SW results i = 10, j = 0, HW = 4.024414, -0.013672, SW = 2.647083, -0.037274
HW and SW results i = 11, j = 0, HW = 4.015625, -0.013672, SW = 2.637882, -0.037213
HW and SW results i = 12, j = 0, HW = 4.033203, -0.012695, SW = 2.655350, -0.036282
HW and SW results i = 13, j = 0, HW = 4.222656, -0.016602, SW = 2.845468, -0.041951
HW and SW results i = 14, j = 0, HW = 4.448242, -0.017578, SW = 3.070912, -0.042820
HW and SW results i = 15, j = 0, HW = 4.807617, -0.013672, SW = 3.429559, -0.040354
HW and SW results i = 16, j = 0, HW = 5.202148, -0.019531, SW = 3.824572, -0.048534
HW and SW results i = 17, j = 0, HW = 5.367188, -0.020508, SW = 3.988451, -0.048833
HW and SW results i = 18, j = 0, HW = 5.325195, -0.026367, SW = 3.945544, -0.056148
HW and SW results i = 19, j = 0, HW = 5.275391, -0.022461, SW = 3.894094, -0.050489
HW and SW results i = 20, j = 0, HW = 5.178711, -0.021484, SW = 3.798736, -0.050703
HW and SW results i = 21, j = 0, HW = 5.010742, -0.020508, SW = 3.631046, -0.050160
HW and SW results i = 22, j = 0, HW = 4.715820, -0.019531, SW = 3.336445, -0.048055
HW and SW results i = 23, j = 0, HW = 4.457031, -0.019531, SW = 3.077446, -0.046769
HW and SW results i = 24, j = 0, HW = 4.337891, -0.018555, SW = 2.958363, -0.044824
HW and SW results i = 25, j = 0, HW = 4.344727, -0.019531, SW = 2.965589, -0.045536
HW and SW results i = 26, j = 0, HW = 4.338867, -0.018555, SW = 2.959619, -0.044858
HW and SW results i = 27, j = 0, HW = 4.303711, -0.018555, SW = 2.924359, -0.044479
HW and SW results i = 28, j = 0, HW = 4.276367, -0.018555, SW = 2.897588, -0.044321
HW and SW results i = 29, j = 0, HW = 4.258789, -0.017578, SW = 2.879802, -0.043693
HW and SW results i = 30, j = 0, HW = 4.239258, -0.018555, SW = 2.860393, -0.044097
HW and SW results i = 31, j = 0, HW = 4.186523, -0.018555, SW = 2.806980, -0.043727
HW and SW results i = 32, j = 0, HW = 4.125000, -0.018555, SW = 2.745974, -0.043355
HW and SW results i = 33, j = 0, HW = 4.058594, -0.017578, SW = 2.679494, -0.042717
HW and SW results i = 34, j = 0, HW = 3.978516, -0.018555, SW = 2.599331, -0.042859
HW and SW results i = 35, j = 0, HW = 3.731445, -0.018555, SW = 2.351973, -0.041944
HW and SW results i = 36, j = 0, HW = 3.646484, -0.018555, SW = 2.267337, -0.041979
HW and SW results i = 37, j = 0, HW = 3.750977, -0.018555, SW = 2.371555, -0.041249
HW and SW results i = 38, j = 0, HW = 3.694336, -0.015625, SW = 2.314963, -0.038042
HW and SW results i = 39, j = 0, HW = 3.620117, -0.015625, SW = 2.241181, -0.040116
HW and SW results i = 40, j = 0, HW = 4.099609, -0.017578, SW = 2.721145, -0.044066
HW and SW results i = 41, j = 0, HW = 4.369141, -0.022461, SW = 2.991379, -0.051047
HW and SW results i = 42, j = 0, HW = 4.442383, -0.018555, SW = 3.064429, -0.045425
HW and SW results i = 43, j = 0, HW = 4.265625, -0.014648, SW = 2.887242, -0.039155
HW and SW results i = 44, j = 0, HW = 3.979492, -0.012695, SW = 2.601302, -0.034550
HW and SW results i = 45, j = 0, HW = 3.593750, -0.013672, SW = 2.215396, -0.034609
HW and SW results i = 46, j = 0, HW = 3.423828, -0.013672, SW = 2.046252, -0.034175
HW and SW results i = 47, j = 0, HW = 3.249023, -0.013672, SW = 1.870888, -0.033923
HW and SW results i = 48, j = 0, HW = 3.207031, -0.013672, SW = 1.828757, -0.033767
HW and SW results i = 49, j = 0, HW = 3.158203, -0.012695, SW = 1.780369, -0.033276
HW and SW results i = 50, j = 0, HW = 3.140625, -0.012695, SW = 1.762675, -0.032938
HW and SW results i = 51, j = 0, HW = 3.123047, -0.012695, SW = 1.745412, -0.033239
HW and SW results i = 0, j = 1, HW = 4.738281, -0.021484, SW = 3.359004, -0.048814
HW and SW results i = 1, j = 1, HW = 4.651367, -0.021484, SW = 3.271967, -0.049351
HW and SW results i = 2, j = 1, HW = 4.590820, -0.021484, SW = 3.210930, -0.049440
HW and SW results i = 3, j = 1, HW = 4.591797, -0.021484, SW = 3.212094, -0.048609

中略

Success HW and SW results match

INFO: [SIM 1] CSim done with 0 errors.
INFO: [SIM 3] *************** CSIM finish ***************


i = 0, j = 0 の時の1 個目のカーネルのHW の数値は 4.335938 で、SW の数値は 2.956438 なので、だいぶ違っているという見方もあるだろう?それは、バイアス値のためだということが分かった。バイアス値を下に示す。
conv_layer_12_180215.png

ソフトウェアで使用する covn1_fbias[0] の値の -2.37814890843 に比べて、ハードウェアで使用する量子化された conv1_bias[0] が -1 であるのが分かると思う。それは、量子化のビット数が全体で 9 ビット、整数部が 1 ビットだからである。つまり整数部の 1 ビットは符号であるので、実質 -1 が最小の数となるためである。この量子化でも畳み込みニューラルネットワークの精度にはさほどの影響を及ぼさないという結論になったためだ。
上の i = 0, j = 0 の時の1 個目のカーネルのHW の数値は 4.335938 だったが、これにソフトウェアで使用する covn1_fbias[0] の値の -2.37814890843 とハードウェアで使用する量子化された conv1_bias[0] の -1 の差分の 1.37814890843 を引いてみると、2.95778909157 となって、SW の数値の 2.956438 とほぼ等しくなることが分かる。

さて、次に、 temp_conv0.bmp と temp_conv1.bmp 、 temp_conv_float0.bmp と temp_conv_float1.bmp を見ていこう。
temp_conv0.bmp を示す。
(2018/02/19 : 修正)
conv_layer_23_180219.png 

temp_conv1.bmp を示す。
(2018/02/19 : 修正)
conv_layer_24_180219.png 

temp_conv_float0.bmp を示す。
(2018/02/19 : 修正)
conv_layer_25_180219.png 

temp_conv_float1.bmp を示す。
(2018/02/19 : 修正)
conv_layer_26_180219.png 

ほとんどハードウェアとソフトウェアの違いは良く分からない?データの処理方法を失敗したかもしれない?

テストベンチのソースコードはこの記事が長くなったので、次の記事に貼っておく。
  1. 2018年02月15日 04:18 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

コメント

コメントの投稿


管理者にだけ表示を許可する

トラックバック URL
http://marsee101.blog.fc2.com/tb.php/4078-8870c688
この記事にトラックバックする(FC2ブログユーザー)