FPGAの部屋 2020年09月
FC2ブログ

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

FPGAの部屋

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

Nexys Video を使ってみよう

Digilent 社の Nexys Video を数年前に Digilent 社の方からいただいた。相当寝せてあったのだが、久しぶりに取り出して使ってみようと思う。
Nexys Video のマニュアル類は”Nexys Video”にある。

まずは、”Vivado Design Suite チュートリアル エンベデッド プロセッサ ハードウェア デザイン UG940 (v2019.2) 2019 年 11 月 26 日”の”第 4 章 演習 3: エンベデッド MicroBlaze プロセ ッサのプログラム”をやってみよう。

そのうち、画像処理用 IP を作って、Nexys Video で動作させてみよう。
  1. 2020年09月30日 21:39 |
  2. Nexys Video
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった8(動作しました)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった7(デバック編 3)”の続き。

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 のスタック容量が足りないのが原因だったようだ。心配していたバイトレーンのエンディアンの影響も無かった。

まずは、Vitis の GUI 画面を示す。mnist_nn_test アプリケーション・プロジェクトを使用する。
mnist_nn_61_200929.png

、”Vitis のデフォルトの Stack size, Heap size は 8k バイトだった”で、スタックサイズを 128 k バイトに拡大した。
mnist_nn_60_200928.png

Vitis の Assistant ウインドウの mnist_nn_test_system -> mnist_nn_test -> Debug を右クリックし、右クリックメニューから Run -> Run Configuration を指定して Run する。
mnist_nn_62_200929.png

Tera Term に結果が表示された。これは正しい。
mnist_nn_68_200929.png

なお、実行時間も計測してみた。ハードウェアが約 2.39 ms 、ソフトウェアが約 2.59 ms で、ハードウェアの方がわずかに速いという結果になった。(なお、NN IP の動作周波数は 50 MHz で、当初の 100 MHz の 1/2 になっている。C コードの合成でのレイテンシは動作周波数 100 MHz で 1.18 ms だった。)

これで正常動作でめでたいのだが、この mnist_nn は Vivado HLS および Vitis HLS のバージョンによって IP の大きさにとっても差があるので、書いておきたい。なお、ソースコードは”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった1(Vivado HLS 編 1)”に貼ってある。

まずは、今使用している Vivado HLS 2019.2 、Vivado HLS 2018.3、Vitis HLS 2020.1、Vivado HLS 2017.4 の Export RTL のレポートを示す。
mnist_nn_64_200929.pngmnist_nn_65_200929.pngmnist_nn_66_200929.pngmnist_nn_67_200929.png

Vivado HLS 2019.2 と 2018.3 の BRAM 使用量は 6 個だが、Vitis HLS 2020.1 の BRAM 使用量は 43 個、Vivado HLS 2017.4 の BRAM 使用量は 42 個だった。何でこんなに違うのだろうか?
Vivado HLS 2019.2 の IP は動作した。Vitis HLS 2020.1 で作った IP も Vivado 2019.2 のブロックデザインに入れてみたが動作した。Vitis HLS 2020.1 の IP のレイテンシは約 400 us なので、Vivado HLS 2019.2 よりも 2 倍以上速い。

最後に現在の mnist_nn_test.c を貼っておく。

// mnist_nn_test.c
// 2020/09/08 by marsee
//

#include <stdio.h>
#include <stdint.h>

#include "xtime_l.h"

#include "af1_weight_float.h"
#include "af1_bias_float.h"
#include "af2_weight_float.h"
#include "af2_bias_float.h"
#include "mnist_data_10.h"
#include "xmnist_nn.h"

int mnist_nn_float(float in[784], float out[10]);
int max_float(float out[10]);
int max_int32_t(int32_t out[10]);

void Xil_DCacheFlush(void);

#define NUM_ITERATIONS    10 // C Simulation
// #define NUM_ITERATIONS    2 // C/RTL CoSimulation

int main(){
    float t_tran_float[NUM_ITERATIONS][784];
    uint8_t t_tran_uint8_t[NUM_ITERATIONS][784];
    int32_t result_hard[NUM_ITERATIONS][10];
    float result_soft[NUM_ITERATIONS][10];
    int max_id_hw, max_id_sw, max_id_ref;
    XMnist_nn mnits_nn_ap;
    int32_t res;
    XTime hw_start_time, hw_end_time;
    XTime sw_start_time, sw_end_time;

    for(int i=0; i<NUM_ITERATIONS; i++){
        for(int j=0; j<784; j++){
            t_tran_float[i][j] = (float)(t_train_256[i][j])/256.0;
            t_tran_uint8_t[i][j] = (uint32_t)(t_train_256[i][j]);
        }
    }
    Xil_DCacheFlush();

    // Initialize tht Device
    int XMinst_status = XMnist_nn_Initialize(&mnits_nn_ap, 0);
    if (XMinst_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XMnist_nn\n");
        return(-1);
    }

    for(int i=0; i<NUM_ITERATIONS; i++){
        u32 char_num = (u32)(&t_tran_uint8_t[i][0]);
        XMnist_nn_Set_in_V(&mnits_nn_ap, char_num);

        XTime_GetTime(&hw_start_time);
        XMnist_nn_Start(&mnits_nn_ap);

        while(!XMnist_nn_IsDone(&mnits_nn_ap));
        XTime_GetTime(&hw_end_time);

        // minst nn result check
        for(int j=0; j<5; j++){
            XMnist_nn_Read_out_V_Words(&mnits_nn_ap, j, &res, 1);
            result_hard[i][j*2] = res & 0x1fff; // 13 bit
            if(result_hard[i][j*2] & 0x1000) // minus
                result_hard[i][j*2] = 0xffffe000 | result_hard[i][j*2]; // Sign extension

            result_hard[i][j*2+1] = (res & 0x1fff0000) >> 16;
            if(result_hard[i][j*2+1] & 0x1000) // minus
                result_hard[i][j*2+1] = 0xffffe000 | result_hard[i][j*2+1]; // Sign extension
        }
        XTime_GetTime(&sw_start_time);
        mnist_nn_float(&t_tran_float[i][0], &result_soft[i][0]);
        XTime_GetTime(&sw_end_time);
        printf("i = %d, HW Execution time = %lf ms, SW Execution time = %lf ms\n", i,
                (double)((long long int)hw_end_time-(long long int)hw_start_time)/333333.0,
                (double)((long long int)sw_end_time-(long long int)sw_start_time)/333333.0);
    }

    int errflag=0;
    for(int i=0; i<NUM_ITERATIONS; i++){
        max_id_hw = max_int32_t(&result_hard[i][0]);
        max_id_sw = max_float(&result_soft[i][0]);
        max_id_ref = max_float(&t_test[i][0]);

        if(max_id_ref != max_id_hw){
            printf("id = %d, max_id_ref = %d, max_id_hw = %d\n", i, max_id_ref, max_id_hw);
            errflag = 1;
        }
        if(max_id_ref != max_id_sw){
            printf("id = %d, max_id_ref = %d, max_id_sw = %d\n", i, max_id_ref, max_id_sw);
            errflag = 1;
        }
    }
    if(errflag == 0)
        printf("No Error\n");

    return(0);
}

int mnist_nn_float(float in[784], float out[10]){
    float dot1[50];
    float dot2[10];

    for(int col=0; col<50; col++){
        dot1[col] = 0;
        for(int row=0; row<784; row++){
            dot1[col] += in[row]*af1_fweight[row][col];
        }
        dot1[col] += af1_fbias[col];

        if(dot1[col] < 0)    // ReLU
            dot1[col] = 0;
    }

    for(int col=0; col<10; col++){
        dot2[col] = 0;
        for(int row=0; row<50; row++){
            dot2[col] += dot1[row]*af2_fweight[row][col];
        }
        dot2[col] += af2_fbias[col];

        if(dot2[col] < 0)    // ReLU
            dot2[col] = 0;
        out[col] = dot2[col];
    }

    return(0);
}

int max_float(float out[10]){
    int max_id;
    float max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}

int max_int32_t(int32_t out[10]){
    int max_id;
    int32_t max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}

  1. 2020年09月29日 05:09 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vitis のデフォルトの Stack size, Heap size は 8k バイトだった

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった5(デバック編 1)”で、Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。 Vivado Analyzer を挿入して AXI インターフェースのアクセスがあるかどうか?を調べてみたところ、アクセスが出てなかった。そして、”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった7(デバック編 3)”で Vitis のアプリケーション・プロジェクトのソフトウェア( mnist_nn_test.c )を小さくすれば動作することが分かった。どうやら、int main() 関数の下に大きな配列を作成したのが原因のようだった。
k林さんに教えていただいたのだが、Vitis のデフォルトの Stack size, Heap size は 8k バイトということだった。これでは、スタックがオーバーフローするのも仕方がない。
k林さんありがとうございました。

具体的には、src -> lscript.ld の Stack Size が 0x2000, Heap Size が 0x2000 だった。両方とも 8k バイトということになる。
mnist_nn_59_200928.png

スタックが 8k バイトではとても足りない。

float t_tran_float[NUM_ITERATIONS][784];

だけでも、float 4 バイト X 10 X 784 = 31,360 で 31k バイトも消費している。
そこで、mnist_nn_test.c の script.ld のスタックの値を 0x20000 、つまり 128 kバイトにしたところ、AXI-Lite インターフェースのトランザクションを確認することができた。これが問題だったようだ。
mnist_nn_60_200928.png
  1. 2020年09月28日 04:37 |
  2. Vitis
  3. | トラックバック:0
  4. | コメント:0

Xilinx 社 AXI インターコネクト IP のAXI4 、AX4I-Lite インターフェースのトランザクション波形

Zynq の PS から Xilinx の AXI インターコネクト IP を通って Vivado HLS で作成した IP における AXI4 や AXI4-Lite インターフェースのトランザクション波形を Vivado Analyzer で取得したので書いておく。

まずは、ブロックデザインを示す。
mnist_nn_34_200925.png

このブロックデザインで ZYNQ7 Processing System の M_AXI_GP0 から ps7_0_axi_periph AXI インターコネクトに接続しているAXI インターフェースと ps7_0_axi_periph AXI インターコネクトから mnist_nn_0 の s_axi_AXILiteS に接続している AXI4-Lite インターフェースの波形を見てみよう。

まずは、Write の波形から。
この Write トランザクションの波形は、

XMnist_nn_Set_in_V(&mnits_nn_ap, char_num);

を実行したときのものだ。
mnist_nn_52_200925.png

processing_system7_0_M_AXI_GP0 と ps7_0_axi_periph_M01_AXI にトランザクションが見える。やはり、BVALID は ps7_0_axi_periph_M01_AXI のWrite が終了してから出力されている。AXI インターフェースでの Write が完了したことを示していているようだ。

次に processing_system7_0_M_AXI_GP0 のトランザクションを詳しく見てみよう。
mnist_nn_53_200925.png

AWLEN が 0 なのでシングル転送だ。よって WLAST もずっと 1 になっている。
0x43C10018 番地に 0x00122460 を書いている。

ps7_0_axi_periph_M00_AXI のトランザクションを見てみよう。
mnist_nn_54_200925.png

こちらは、AXI-Lite インターフェースなので、信号が少ない。


Read のトランザクションを見てみよう。
この Read のトランザクションは

while(!XMnist_nn_IsDone(&mnits_nn_ap));

を実行したときのものだ。
mnist_nn_56_200927.png

processing_system7_0_M_AXI_GP0 と ps7_0_axi_periph_M01_AXI にトランザクションが見える。当然だが、processing_system7_0_M_AXI_GP0 の Read トランザクションは ps7_0_axi_periph_M01_AXI の Read トランザクションの前から開始されて、ps7_0_axi_periph_M01_AXI の Read トランザクションが終了してから終了している。

processing_system7_0_M_AXI_GP0 のトランザクションを見てみよう。
mnist_nn_57_200927.png

AXI4 インターフェースの ARLEN はシングル転送なので 0 となっている。 RLAST はデータが来る 1 クロック前に 1 になっている。

ps7_0_axi_periph_M00_AXI のトランザクションを見てみよう。
mnist_nn_58_200927.png

AXI4-Lite インターフェースだ。

Zynq の PS から Xilinx の AXI インターコネクト IP を通って Vivado HLS で作成した IP における AXI4 や AXI4-Lite インターフェースのトランザクション波形を Vivado Analyzer で見てきたが、いろいろと気づきがあった。
Write の Response Channel の波形が興味深かった。
  1. 2020年09月27日 06:08 |
  2. AXI4バス
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった7(デバック編 3)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった6(デバック編 2)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、Vivado Analyzer を挿入して AXI-Lite インターフェースのアクセスがあるかどうか?を調べたが、NN IP のアクセスは無かった。前回は、この構成でAXI-Lite インターフェースのアクセスがあるか?を調べるために DMA_pow2 IP (2乗 IP)を Add IP してアクセスを調べたところ、問題なくアクセスが来ていた。今回は、NN IP でもアクセスが来るようになったので、その顛末を書いておく。

もしかして、制御用のアプリケーション・ソフトウェアが多すぎるのか?と思い、ソフトウェアでの NN 計算を止めることにした。そうすると、重みやバイアスが無くなるので、大きくプログラムサイズが減ることになる。そこで、その部分を削除したソフトウェアを書いた。
新しい、mnist_nn_test.c を示す。

// mnist_nn_test.c
// 2020/09/08 by marsee
// 2020/09/24 : removed weights and biases.
//

#include <stdio.h>
#include <stdint.h>

#include "mnist_data_10.h"
#include "xmnist_nn.h"

int max_float(float out[10]);
int max_int32_t(int32_t out[10]);

#define NUM_ITERATIONS    10 // C Simulation
// #define NUM_ITERATIONS    2 // C/RTL CoSimulation

int main(){
    uint8_t t_tran_uint8_t[NUM_ITERATIONS][784];
    int32_t result_hard[NUM_ITERATIONS][10];
    int max_id_hw, max_id_ref;
    XMnist_nn mnits_nn_ap;
    int32_t res;

    for(int i=0; i<NUM_ITERATIONS; i++){
        for(int j=0; j<784; j++){
            t_tran_uint8_t[i][j] = (uint8_t)(t_train_256[i][j]);
        }
    }

    // Initialize tht Device
    int XMinst_status = XMnist_nn_Initialize(&mnits_nn_ap, 0);
    if (XMinst_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XMnist_nn\n");
        return(-1);
    }

    for(int i=0; i<NUM_ITERATIONS; i++){
        u32 char_num = (u32)(&t_tran_uint8_t[i][0]);
        XMnist_nn_Set_in_V(&mnits_nn_ap, char_num);
        XMnist_nn_Start(&mnits_nn_ap);

        while(!XMnist_nn_IsDone(&mnits_nn_ap));

        // minst nn result check
        for(int j=0; j<5; j++){
            XMnist_nn_Read_out_V_Words(&mnits_nn_ap, j, &res, 1);
            result_hard[i][j*2] = res & 0x1fff; // 13 bit
            if(result_hard[i][j*2] & 0x1000) // minus
                result_hard[i][j*2] = 0xffffe000 | result_hard[i][j*2]; // Sign extension

            result_hard[i][j*2+1] = (res & 0x1fff0000) >> 16;
            if(result_hard[i][j*2+1] & 0x1000) // minus
                result_hard[i][j*2+1] = 0xffffe000 | result_hard[i][j*2+1]; // Sign extension
        }
    }

    int errflag=0;
    for(int i=0; i<NUM_ITERATIONS; i++){
        max_id_hw = max_int32_t(&result_hard[i][0]);
        max_id_ref = max_float(&t_test[i][0]);

        if(max_id_ref != max_id_hw){
            printf("id = %d, max_id_ref = %d, max_id_hw = %d\n", i, max_id_ref, max_id_hw);
            errflag = 1;
        }
    }
    if(errflag == 0)
        printf("No Error\n");

    return(0);
}

int max_float(float out[10]){
    int max_id;
    float max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}

int max_int32_t(int32_t out[10]){
    int max_id;
    int32_t max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}


これを新規作成した mnist_nn_test2 アプリケーション・プログラムに入れた。
mnist_nn_50_200926.png

Debug を行って、

XMnist_nn_Set_in_V(&mnits_nn_ap, char_num);

を実行したところ、AXI4-Lite インターフェースに Write アクセスが発生した。
AXI-Lite インターフェースが動作している部分の拡大波形を示す。
mnist_nn_52_200925.png

processing_system7_0_M_AXI_GP0 と ps7_0_axi_periph_M01_AXI にトランザクションが見える。

processing_system7_0_M_AXI_GP0 のトランザクションを見てみよう。
mnist_nn_53_200925.png

0x43C10018 番地に 0x00122460 を書いている。

ps7_0_axi_periph_M00_AXI のトランザクションを見てみよう。
mnist_nn_54_200925.png

最後まで Run すると、結果が表示された。
すべての結果が 8 というのがおかしいけれど、AXI4-Lite インターフェースのアクセスは確認できた。
mnist_nn_55_200925.png

やはり、プログラムが多すぎるのが行けないのか?
配列もローカル変数で取っているが、スタックに配置されると思うので、大きな配列を取るのはまずいだろうか? malloc() でヒープに取ってみよう。
  1. 2020年09月26日 18:10 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった6(デバック編 2)

”Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった5(デバック編 1)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、Vivado Analyzer を挿入して AXI-Lite インターフェースのアクセスがあるかどうか?を調べたが、アクセスは無かった。今回は、この構成でAXI-Lite インターフェースのアクセスがあるか?を調べるために DMA_pow2 IP (2乗 IP)を Add IP してアクセスを調べてみる。

Vivado HLS 2019.2 の DMA_pow2 プロジェクトを示す。
DMA_pow2 は 10 個の配列を DMA Read で読んできて、それらを 2 乗して DMA Write する IP となっている。
mnist_nn_33_200925.png

これを Export RTL して IP にした。
mnist_nn_38_200925.png

これを Vivado 2019.2 の mnist_nn_test プロジェクトの IP Catalog に追加した。
mnist_nn_37_200925.png

これで使えるようになったので、ブロックデザインに DMA_pow2 を追加し、AXI-Lite インターフェースに Debug を設定した。
mnist_nn_34_200925.png

Address Editor を示す。
mnist_nn_35_200925.png

論理合成、インプリメンテーション、ビットストリームの生成を行った。
mnist_nn_36_200925.png

50 MHz なので余裕がある。

XSA ファイルを出力して、Vitis のプラットフォームをアップデートした。mnist_nn_test アプリケーション・プロジェクトも再ビルドした。
DMA_pow2 アプリケーション・プロジェクトを作成して、ビルド成功した。
mnist_nn_39_200925.png

DMA_pow2 アプリケーション・プロジェクトの dma_test.elf をデバックモードで起動した。
mnist_nn_40_200925.png

Vivado の Flow Navigator で PROGRAM AND DEBUG -> Open Hardware Manager -> Open Target をクリックし、メニューから Auto Connect を選択する。
自動的に Vivado Analyzer が起動する。
mnist_nn_41_200925.png

slot 0 ~ 2 の AXI4 インターフェースの AWVALID, ARVALID を OR でトリガーをかけた。

Vitis のデバックモードで

XDma_pow2_Set_in_r(&XDMA_pow2_ap, (u32)&data[0]);

を過ぎたときにトリガーがかかった。
mnist_nn_42_200925.png

AXI-Lite インターフェースが動作している部分の拡大波形を示す。
mnist_nn_43_200925.png

processing_system7_0_M_AXI_GP0 と ps7_0_axi_periph_M01_AXI にトランザクションが見える。

processing_system7_0_M_AXI_GP0 のトランザクションを見てみよう。
mnist_nn_44_200925.png

0x43C10018 番地に 0x0010b234 を書いている。

ps7_0_axi_periph_M01_AXI のトランザクションを見てみよう。
mnist_nn_45_200925.png

0x18 番地に 0x0010b234 を書いている。

次に、Vitis のデバックモードで

XDma_pow2_Set_out_r(&XDMA_pow2_ap, (u32)&result[0]);

を過ぎたときに Vivado Analyzer のトリガーがかかった。
mnist_nn_46_200925.png

processing_system7_0_M_AXI_GP0 のトランザクションを見た。
mnist_nn_47_200925.png

0x43C10020 番地に 0x00110318 を書いている。

ps7_0_axi_periph_M01_AXI のトランザクションを見てみよう。
mnist_nn_48_200925.png

0x43C10020 番地に 0x00110318 を書いている。

Vitis で最後までソフトウェアを走らせると Tera Term に計算結果が表示された。
mnist_nn_49_200925.png

DMA_pow2 は正常に動作している。
  1. 2020年09月25日 04:47 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった5(デバック編 1)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった4(Vitis 編)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、 XSA ファイルを使用して Vitis 2019.2 のプラットフォームを作成し、アプリケーション・プロジェクトを作成して、実機で検証したが動作しなかった。今回は Vivado Analyzer を挿入して AXI インターフェースのアクセスがあるかどうか?を調べてみよう。

Vivado のブロックデザインで、ZYNQ7 Processing System の M_AXI_GP0 ポートと mnist_nn_0 の s_axi_AXILiteS ポートに Debug を設定した。
mnist_nn_25_200924.png

Save してから論理合成、インプリメンテーション、ビットストリームの生成を行った。
Project Summary を示す。
mnist_nn_26_200924.png

問題ない。
XSA ファイルを出力してから、Vitis でプラットフォームを Update Hardware Specification を行って、更新された XSA ファイルを読み込んだ。
プラットフォームもアプリケーション・プロジェクトも再ビルドを行った。

Vitis をデバッカー・モードで起動した。
mnist_nn_27_200924.png

Vivado の Flow Navigator で PROGRAM AND DEBUG -> Open Hardware Manager -> Open Target をクリックし、メニューから Auto Connect を選択する。
自動的に Vivado Analyzer が起動する。
mnist_nn_28_200924.png

ps7_0_axi_periph_M00_AXI: AWVALID と processing_system7_0_M_AXI_GP0: AWVALID 立ち上がりの OR でトリガーがかかるように設定して、トリガー待ち状態にした。
mnist_nn_29_200924.png

Vitis でデバックを進めていって、XMnist_nn_Set_in_V() のところで止めた。ここでは mnist_nn IP の AXI4-Lite インターフェース経由で in が DMA Read するためにアドレスを ZYNQ7 Processing System から mnist_nn_0 に書き込まれるはずだ。
mnist_nn_30_200924.png

実際にデータを Write する画面になった。
mnist_nn_31_200924.png

ここを過ぎて DataAbortHandler の画面になった。
mnist_nn_32_200924.png

こうなっても、Vivado Analyzer はトリガを待ち続けている。
mnist_nn_29_200924.png

processing_system7_0_M_AXI_GP0 からのアクセスが来ないようだ?
なぜだろうか?なぜ AXI4-Lite のアクセスが来ない?

ここが間違っているとかの情報をお待ちしております。どこが悪いんでしょうか?
  1. 2020年09月24日 04:46 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった4(Vitis 編)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった3(Vivado 編)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は Vivado 2019.2 を使用して、ブロックデザインを作成し、論理合成、インプリメンテーション、ビットストリームの生成を行い、XSA ファイルを作成した。今回は、その XSA ファイルを使用して Vitis 2019.2 のプラットフォームを作成し、アプリケーション・プロジェクトを作成して、実機で検証する。

もうすでに、プラットフォームとアプリケーション・プロジェクトを作成済みの Vitis 2019.2 を示す。前回作成した XSA ファイルを使用してプラットフォームを作成してある。
mnist_nn_17_200923.png

アプリケーション・ソフトウェアの mnist_nn_test.c を示す。

// mnist_nn_test.c
// 2020/09/08 by marsee
//

#include <stdio.h>
#include <stdint.h>

#include "af1_weight_float.h"
#include "af1_bias_float.h"
#include "af2_weight_float.h"
#include "af2_bias_float.h"
#include "mnist_data_10.h"
#include "xmnist_nn.h"

int mnist_nn_float(float in[784], float out[10]);
int max_float(float out[10]);
int max_int32_t(int32_t out[10]);

#define NUM_ITERATIONS    10 // C Simulation
// #define NUM_ITERATIONS    2 // C/RTL CoSimulation

int main(){
    float t_tran_float[NUM_ITERATIONS][784];
    uint8_t t_tran_uint8_t[NUM_ITERATIONS][784];
    int32_t result_hard[NUM_ITERATIONS][10];
    float result_soft[NUM_ITERATIONS][10];
    int max_id_hw, max_id_sw, max_id_ref;
    XMnist_nn mnits_nn_ap;
    int mnist_nn_isdone = 0;
    int32_t res;

    printf("Hello World\n");

    for(int i=0; i<NUM_ITERATIONS; i++){
        for(int j=0; j<784; j++){
            t_tran_float[i][j] = (float)(t_train_256[i][j])/256.0;
            t_tran_uint8_t[i][j] = (uint32_t)(t_train_256[i][j]);
        }
    }

    // Initialize tht Device
    //printf("a"); fflush(stdout);
    int XMinst_status = XMnist_nn_Initialize(&mnits_nn_ap, 0);
    if (XMinst_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XMnist_nn\n");
        return(-1);
    }

    for(int i=0; i<NUM_ITERATIONS; i++){
        //printf("a"); fflush(stdout);
        u32 char_num = (u32)(&t_tran_uint8_t[i][0]);
        XMnist_nn_Set_in_V(&mnits_nn_ap, char_num);
        //printf("a"); fflush(stdout);
        XMnist_nn_Start(&mnits_nn_ap);

        while(mnist_nn_isdone == 0)
            mnist_nn_isdone = XMnist_nn_IsDone(&mnits_nn_ap);

        // minst nn result check
        for(int j=0; j<5; j++){
            XMnist_nn_Read_out_V_Words(&mnits_nn_ap, i, &res, 1);
            result_hard[i][j*2] = res & 0x1fff; // 13 bit
            if(result_hard[i][j*2] & 0x1000) // minus
                result_hard[i][j*2] = 0xffffe000 | result_hard[i][j*2]; // Sign extension

            result_hard[i][j*2+1] = (res & 0x1fff0000) >> 16;
            if(result_hard[i][j*2+1] & 0x1000) // minus
                result_hard[i][j*2+1] = 0xffffe000 | result_hard[i][j*2+1]; // Sign extension
        }

        mnist_nn_float(&t_tran_float[i][0], &result_soft[i][0]);
    }

    int errflag=0;
    for(int i=0; i<NUM_ITERATIONS; i++){
        max_id_hw = max_int32_t(&result_hard[i][0]);
        max_id_sw = max_float(&result_soft[i][0]);
        max_id_ref = max_float(&t_test[i][0]);

        if(max_id_ref != max_id_hw){
            printf("id = %d, max_id_ref = %d, max_id_hw = %d\n", i, max_id_ref, max_id_hw);
            errflag = 1;
        }
        if(max_id_ref != max_id_sw){
            printf("id = %d, max_id_ref = %d, max_id_sw = %d\n", i, max_id_ref, max_id_sw);
            errflag = 1;
        }
    }
    if(errflag == 0)
        printf("No Error\n");

    return(0);
}

int mnist_nn_float(float in[784], float out[10]){
    float dot1[50];
    float dot2[10];

    for(int col=0; col<50; col++){
        dot1[col] = 0;
        for(int row=0; row<784; row++){
            dot1[col] += in[row]*af1_fweight[row][col];
        }
        dot1[col] += af1_fbias[col];

        if(dot1[col] < 0)    // ReLU
            dot1[col] = 0;
    }

    for(int col=0; col<10; col++){
        dot2[col] = 0;
        for(int row=0; row<50; row++){
            dot2[col] += dot1[row]*af2_fweight[row][col];
        }
        dot2[col] += af2_fbias[col];

        if(dot2[col] < 0)    // ReLU
            dot2[col] = 0;
        out[col] = dot2[col];
    }

    return(0);
}

int max_float(float out[10]){
    int max_id;
    float max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}

int max_int32_t(int32_t out[10]){
    int max_id;
    int32_t max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}


ZYBO Z7-10 とパソコンを USB ケーブルで接続して、電源を ON にした。
Tera Term を起動した。
Vitis で mnist_nn_test.elf をデバックモードで起動した。
mnist_nn_18_200923.png

Step Over でプログラムを進めていく。
XMnist_nn_Initialize() を実行すると mnist_nn_ap 構造体に値が入った。アドレスの 0x43C00000 も入っている。
mnist_nn_19_200923.png

XMnist_nn_Set_in_V() を実行したところで、止まってしまっている。
mnist_nn_20_200923.png

今までデバッカーを Step Over で実行していたが、XMnist_nn_Set_in_V() を実行するところで、 Step Into に切り替える。
そうすると、ドライバの XMnist_nn_Set_in_V() 関数に来た。
mnist_nn_21_200923.png

XMnist_nn_Set_in_V() 関数の中の XMnist_nn_WriteReg() 関数に飛ぶ。
mnist_nn_22_200923.png

Xil_out32() 関数に飛んで、Value を LocalAddr に書き込む。
LocalAddr は 0x43C00018 で ” 0x18 : Data signal of in_r ”を指しているので、問題ない。
mnist_nn_23_200923.png

だが、これを実行すると DataAbortHandler に飛んでしまうのだ。
mnist_nn_24_200923.png

0x48C00018 番地に書けないようだ。これは困った。なぜだろうか?
  1. 2020年09月23日 04:31 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった3(Vivado 編)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった2(Vivado HLS 編 2)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は Vivado HLS の C/RTL 協調シミュレーションを行って正常動作することを確認し、Export RTL で IP 化を行った。今回は、 Vivado 2019.2 を使用して、ブロックデザインを作成し、論理合成、インプリメンテーション、ビットストリームの生成を行い、XSA ファイルを作成した。

Vivado 2019.2 を起動して、ZYBO Z7-10 用の mnist_nn_test プロジェクトを作成した。
Vivado プロジェクトのフォルダ直下に mnist_nn フォルダを作って、Vivado HLS で Export RTL で出力した ZIP 圧縮の IP の xilinx_com_hls_mnist_nn_1_0.zip を展開した。

Vivado HLS プロジェクトの solution1/impl/ip フォルダ
mnist_nn_15_200922.png

Vivado プロジェクト・フォルダ
mnist_nn_13_200922.png

Vivado 2019.2 の mnist_nn_test プロジェクトを示す。もうビットファイルを生成済みだ。
mnist_nn_8_200922.png

mnist_nn IP を IP Catalog に登録した。
mnist_nn_12_200922.png

mnist_nn_bd ブロックデザインを作成した。
mnist_nn_9_200922.png

なお PL のクロックは 50 MHz とした。
mnist_nn_10_200922.png

Address Editor を示す。
mnist_nn_11_200922.png

論理合成、インプリメンテーション、ビットストリームの生成を行って成功した。
Project Summary を示す。
mnist_nn_16_200922.png

Export Hardware を行った。
mnist_nn_14_200922.png
  1. 2020年09月22日 05:04 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった2(Vivado HLS 編 2)

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった1(Vivado HLS 編 1)”の続き。

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにしたということで、前回は、Vivado HLS プロジェクトを作成し、C シミュレーションを行った。今回は、C コードの合成、C/RTL協調シミュレーション、Export RTL を行った。

C コードの合成を行った。
mnist_nn_3_200920.png

レイテンシは 118745 クロック、1.187 ms だった。リソース使用量は BRAM_18K が 42 個、DSP48E が 1 個、FF が 1167 個、LUT が 2020 個だった。

C/RTL 協調シミュレーションを行った。
mnist_nn_4_200920.png

レイテンシは、119473 クロックだった。

C/RTL協調シミュレーションの波形を示す。
全体波形から。10 回、回路を動作させている。
mnist_nn_5_200920.png

切れ目を拡大した。
AXI4 Lite インターフェースで out[10] を出力すると、次に手書き数字の認識に入って、AXI4 Lite インターフェースで Write し、回路動作をスタートさせている。AXI4 インターフェースでは、Master 機能によって手書き数字データを Read している。
mnist_nn_6_200920.png

Export RTL を行った。結果を示す。
mnist_nn_7_200920.png

SLICE が 1905 個、LUT が 7025 個、FF が 1543 個、DSP が 4 個、BRAM が 4 個、 SRL が 41 個だった。
C コードの合成と比べて、特に BRAM は 1/10 になってしまったので、少なすぎではないだろうか?
  1. 2020年09月21日 04:49 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2019.2 で合成した IP を Vivado で使ったが動作しなかった1(Vivado HLS 編 1)

Vivado HLS 2019.2 でニューラルネットワークの IP を作成し、Vivado で IP を使用して回路を作成したが、動作しなかった。その顛末を書くことにする。

ソースコードの mnist_nn.cpp を示す。

// mnist_nn.cpp
// 2017/06/01 by marsee
//

#include <stdio.h>
#include <ap_fixed.h>

#include "af1_weight.h"
#include "af1_bias.h"
#include "af2_weight.h"
#include "af2_bias.h"

int mnist_nn(ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> in[784], ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> out[10]){
#pragma HLS DATAFLOW
#pragma HLS INTERFACE s_axilite register port=out
#pragma HLS INTERFACE m_axi depth=784 port=in offset=slave
#pragma HLS INTERFACE s_axilite port=return
    ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> buf[784];
    ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> dot1[50];
    ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> dot2[10];

    buf_copy: for(int i=0; i<784; i++)
#pragma HLS PIPELINE II=1
        buf[i] = in[i];

    af1_dot1: for(int col=0; col<50; col++){
        dot1[col] = 0;
        af1_dot2: for(int row=0; row<784; row++){
#pragma HLS PIPELINE II=3
            dot1[col] += buf[row]*af1_weight[row][col];
        }
        dot1[col] += af1_bias[col];

        if(dot1[col] < 0)   // ReLU
            dot1[col] = 0;
    }

    af2_dot1: for(int col=0; col<10; col++){
        dot2[col] = 0;
        af2_dot2: for(int row=0; row<50; row++){
#pragma HLS PIPELINE II=1
            dot2[col] += dot1[row]*af2_weight[row][col];
        }
        dot2[col] += af2_bias[col];

        if(dot2[col] < 0)   // ReLU
            dot2[col] = 0;
        out[col] = dot2[col];
    }

    return(0);
}


テストベンチの mnist_nn_tb.cpp を示す。

// mnist_nn_tb.cpp
// 2017/06/02 by marsee
//

#include <stdio.h>
#include <ap_fixed.h>

#include "af1_weight.h"
#include "af1_bias.h"
#include "af2_weight.h"
#include "af2_bias.h"
#include "mnist_data_10.h"
//#include "mnist_data.h"

int mnist_nn(ap_ufixed<8, 0, AP_TRN_ZERO, AP_SAT> in[784], ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> out[10]);
int mnist_nn_float(float in[784], float out[10]);
int max_ap_fixed(ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> out[10]);
int max_float(float out[10]);

#define NUM_ITERATIONS    10 // C Simulation
// #define NUM_ITERATIONS    2 // C/RTL CoSimulation

int main(){
    float t_tran_float[NUM_ITERATIONS][784];
    ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> result_ap_fixed[NUM_ITERATIONS][10];
    float result_float[NUM_ITERATIONS][10];
    int max_id_hw, max_id_sw, max_id_ref;

    for(int i=0; i<NUM_ITERATIONS; i++)
        for(int j=0; j<784; j++)
            t_tran_float[i][j] = (float)t_train[i][j];

    for(int i=0; i<NUM_ITERATIONS; i++){
        mnist_nn(&t_train[i][0], &result_ap_fixed[i][0]);
        mnist_nn_float(&t_tran_float[i][0], &result_float[i][0]);
    }

    int errflag=0;
    for(int i=0; i<NUM_ITERATIONS; i++){
        max_id_hw = max_ap_fixed(&result_ap_fixed[i][0]);
        max_id_sw = max_float(&result_float[i][0]);
        max_id_ref = max_float(&t_test[i][0]);

        if(max_id_ref != max_id_hw){
            printf("id = %d, max_id_ref = %d, max_id_hw = %d\n", i, max_id_ref, max_id_hw);
            errflag = 1;
        }
        if(max_id_ref != max_id_sw){
            printf("id = %d, max_id_ref = %d, max_id_sw = %d\n", i, max_id_ref, max_id_sw);
            errflag = 1;
        }
    }
    if(errflag == 0)
        printf("No Error\n");

    return(0);
}

int mnist_nn_float(float in[784], float out[10]){
    float dot1[50];
    float dot2[10];

    af1_dot1: for(int col=0; col<50; col++){
        dot1[col] = 0;
        af1_dot2: for(int row=0; row<784; row++){
            dot1[col] += in[row]*af1_fweight[row][col];
        }
        dot1[col] += af1_fbias[col];

        if(dot1[col] < 0)    // ReLU
            dot1[col] = 0;
    }

    af2_dot1: for(int col=0; col<10; col++){
        dot2[col] = 0;
        af2_dot2: for(int row=0; row<50; row++){
            dot2[col] += dot1[row]*af2_fweight[row][col];
        }
        dot2[col] += af2_fbias[col];

        if(dot2[col] < 0)    // ReLU
            dot2[col] = 0;
        out[col] = dot2[col];
    }

    return(0);
}

int max_ap_fixed(ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> out[10]){
    int max_id;
    ap_fixed<13, 5, AP_TRN_ZERO, AP_SAT> max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}

int max_float(float out[10]){
    int max_id;
    float max;

    for(int i=0; i<10; i++){
        if(i == 0){
            max = out[0];
            max_id = 0;
        }else if(out[i]>max){
            max = out[i];
            max_id = i;
        }
    }
    return(max_id);
}


Vivado HLS 2019.2 で作成した mnist_nn プロジェクトを示す。
mnist_nn_1_200920.png

C シミュレーション結果を示す。
10 個の手書き数字を認識して、1 個、間違っている。
mnist_nn_2_200920.png
  1. 2020年09月20日 04:05 |
  2. Vivado HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その8 (AXI4-Stream インターフェース 2)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その7 (AXI4-Stream インターフェース 1)”の続き。

AXI4-Stream インターフェース機能の 2 乗回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較するということで、前回は、C シミュレーションと C コードの合成を行った。今回は、C/RTL 協調シミュレーションと Export RTL を行う。

C/RTL 協調シミュレーションを行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_104_200917.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_105_200917.png


Vitis HLS が 51 クロック、 VIvado HLS が 58 クロックで、C コードの合成の差よりも差が少ない感じがするが、どうしてだろうか?
波形を見て確認してみよう。

C/RTL 協調シミュレーションの波形を確認する。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_106_200917.png

やはり、前振りが長いので、データ転送している部分を拡大する。
Vitis_HLS_vs_Vivado_HLS_107_200917.png

データ転送は 2 クロックに 1 転送になっているが、最初のレイテンシがあるようだ。
AXI4 Lite インターフェースでスタートとして、 0 番地に 1 を書いてから、転送が終了するまでは 310 ns となっている。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_108_200917.png

Vivado HLS は、データ転送は 3 クロックに 1 転送になっている。最初のレイテンシはほぼ Vitis HLS のレイテンシと同じ時間のようだ。
AXI4 Lite インターフェースでスタートとして、 0 番地に 1 を書いてから、転送が終了するまでは 370 ns となっている。


Export RTL を行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_109_200917.png

リソースは Vitis HLS の方が消費しているが、 CP achieved post-implementation は 5.692 ns と短い。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_110_200917.png

リソースは Vitis HLS よりも消費していないが、CP achieved post-implementation は 8.750 ns と長い。

  1. 2020年09月18日 21:14 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その7 (AXI4-Stream インターフェース 1)

”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/RTL 協調シミュレーションと Export RTL を行った。今回は、AXI4-Stream インターフェース機能の 2 乗回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。今回は、 C シミュレーションと C コードの合成を行う。

まずは、ソースコードの pow2_axis.cpp から貼っておく。

// pow2_axis.cpp (2018/05/16 by marsee)

#include <ap_int.h>
#include <hls_stream.h>
#include <ap_axi_sdata.h>

int pow2_axis(hls::stream<ap_axis<32,1,1,1> >& ins, hls::stream<ap_axis<32,1,1,1> >& outs){
#pragma HLS INTERFACE s_axilite port=return
#pragma HLS INTERFACE axis register both port=outs
#pragma HLS INTERFACE axis register both port=ins
    ap_axis<32,1,1,1> val;

    Loop1 : do {    // user が 1になった時にフレームがスタートする
#pragma HLS LOOP_TRIPCOUNT min=1 max=1 avg=1
        ins >> val;
    } while(val.user == 0);

    Loop2 : for(int i=0; i<10; i++){
        if(i != 0)
            ins >> val;

        val.data = val.data * val.data;

        outs << val;
    }

    return(0);
}


テストベンチの pow2_axis_tb.cpp を示す。

// pow2_axis_tb.cpp (2018/05/16 by marsee)

#include <ap_int.h>
#include <hls_stream.h>
#include <iostream>
#include <ap_axi_sdata.h>

int pow2_axis(hls::stream<ap_axis<32,1,1,1> >& ins, hls::stream<ap_axis<32,1,1,1> >& outs);
#define END_DATA_NUM    10

int main(){
    using namespace std;

    hls::stream<ap_axis<32,1,1,1> > ins;
    hls::stream<ap_axis<32,1,1,1> > outs;
    ap_axis<32,1,1,1> streamd;
    ap_axis<32,1,1,1> vals;

    // ins に入力データを用意する
    for(int i=0; i<5; i++){ // dummy data
        streamd.user = 0;
        streamd.data = i;
        ins << streamd;
    }
    for(int i=0; i<END_DATA_NUM; i++){
        streamd.data = i;
        if(i == 0)
            streamd.user = 1;
        else
            streamd.user = 0;
        if(i == END_DATA_NUM-1)
            streamd.last = 1;
        else
            streamd.last = 0;
        ins << streamd;
    }

    pow2_axis(ins, outs);

    cout << endl;
    cout << "outs" << endl;
    for(int i=0; i<END_DATA_NUM; i++){
        outs >> vals;
        cout << "i = " << i << " result = " << vals.data << " vals.user = "
                << vals.user << " vals.last = " << vals.last << endl;
    }
    return(0);
}


pow2_axis プロジェクトを示す。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_96_200917.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_97_200917.png


C シミュレーションを行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_98_200917.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_99_200917.png


相変わらず、C シミュレーションに差はない。

C コードの合成を行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_100_200917.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_101_200917.png


Vitis HLS のレイテンシは 26 クロックで、Vivado HLS のレイテンシは 32 クロックだった。例によって Vitis HLS の方がレイテンシが短い。リソース使用量は、Vitis HLS の方が Vivado HLS よりも多くなっている。

Analysis 画面を見てみよう。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_102_200917.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_103_200917.png


Vitis HLS は 8 ステートだが、Vivado HLS は 5 ステートだった。この辺りにも最適化の違いがでてくるようだ。
  1. 2020年09月17日 05:14 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その6 (AXI4 インターフェースの Master 機能2)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その5 (AXI4 インターフェースの Master 機能1)”の続き。

AXI4 インターフェースの Master 機能の 2 乗回路を使用して、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。
前回は、 C シミュレーションと C コードの合成を行った。今回は、C/RTL 協調シミュレーションと Export RTL を行う。

まずは、C/RTL 協調シミュレーションを行った。Dump Trace を all にして、波形を記録するように設定を行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_89_200916.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_90_200916.png


前回、確認したように、合成された回路の性能が Vitis HLS の方が格段に良かったので、C/RTL 協調シミュレーションの結果にも差が付いている。Vitis HLS は 90 クロックで、Vivado HLS は 235 クロックだった。

C/RTL 協調シミュレーションの波形を確認してみよう。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_91_200916.png

Vitis HLS は全体波形に対する有効な波形の割合が小さいので、必要な部分を拡大する。
Vitis_HLS_vs_Vivado_HLS_92_200916.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_93_200916.png


Export RTL を行った。Vivado synthesis, place and route にチェックを入れた。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_94_200916.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_95_200916.png


Vivado HLS 2020.1 の方がリソース使用量が少ない。

やはり、デフォルトで合成された回路の品質に差があるので、結果が異なっている。
  1. 2020年09月16日 05:03 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その5 (AXI4 インターフェースの Master 機能1)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その4 (AXI4 Lite インターフェースの Slave 機能)”の続き。

前回は、AXI4 インターフェースの Slave 機能の簡単な乗算回路を使って、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較した。今回は、AXI4 インターフェースの Master 機能の 2 乗回路を使用して、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較する。今回の行うのは C シミュレーションと C コードの合成だ。

まずは、ソースコードの DMA_pow2.cpp を示す。

// DMA_pow2.cpp
// 2018/05/08 by marsee
//

int DMA_pow2(volatile int *in, volatile int *out){
#pragma HLS INTERFACE m_axi depth=10 port=out offset=slave
#pragma HLS INTERFACE m_axi depth=10 port=in offset=slave
#pragma HLS INTERFACE s_axilite port=return

    for (int i=0; i<10; i++){
        out[i] =in[i] * in[i];
    }

    return(0);
}


次に、テストベンチの DMA_pow2_tb.cpp を示す。

// DMA_pow2_tb.cpp
// 2018/05/08 by marsee
//

#include <iostream>

int DMA_pow2(volatile int *in, volatile int *out);

int main(){
    int data[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
    int result[10];

    DMA_pow2(data, result);

    for(int i=0; i<10; i++){
        std::cout << "data[" << i << "]= " << data[i] <<
                ", result[" << i << "] = " <<
                result[i] << std::endl;
    }
}


Vitis HLS 2020.1 と Vivado HLS 2020.1 の DMA_pow2 プロジェクトを示す。

Vitis 2020.1
Vitis_HLS_vs_Vivado_HLS_79_200915.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_80_200915.png


C シミュレーションを行った。デフォルトでの C シミュレーションに違いはない。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_81_200915.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_82_200915.png


C コードの合成を行った。

Vitis 2020.1
Vitis_HLS_vs_Vivado_HLS_83_200915.png

全体の Latency が 26 クロックで 260 ns だった。速い。
VITIS_LOOP_10_1 のループの Interval が 1 で自動的にパイプラインされている。PIPELINE 指示子は付加していないが、自動的にパイプラインされてしまうようだ。ということは、2 回 in[i] を読んでいなくて、最適化もされているようだ。結構、Vivado HLS に比べて違うようだ。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_85_200915.png

Latency は 126 クロック、 1.26 us で遅い。パイプラインもされていない。これから指示子を追加していく状態だ。


C コードの合成で生成された Verilog HDL ファイルを見ていこう。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_84_200915.png

4 個の Verilog HDL ファイルが生成さえている。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_86_200915.png

3 個の Verilog HDL ファイルが生成されている。


DMA_pow2.v の 入出力のポートを比較する。

Vitis HLS 2020.1

module DMA_pow2 (
        ap_clk,
        ap_rst_n,
        m_axi_gmem_AWVALID,
        m_axi_gmem_AWREADY,
        m_axi_gmem_AWADDR,
        m_axi_gmem_AWID,
        m_axi_gmem_AWLEN,
        m_axi_gmem_AWSIZE,
        m_axi_gmem_AWBURST,
        m_axi_gmem_AWLOCK,
        m_axi_gmem_AWCACHE,
        m_axi_gmem_AWPROT,
        m_axi_gmem_AWQOS,
        m_axi_gmem_AWREGION,
        m_axi_gmem_AWUSER,
        m_axi_gmem_WVALID,
        m_axi_gmem_WREADY,
        m_axi_gmem_WDATA,
        m_axi_gmem_WSTRB,
        m_axi_gmem_WLAST,
        m_axi_gmem_WID,
        m_axi_gmem_WUSER,
        m_axi_gmem_ARVALID,
        m_axi_gmem_ARREADY,
        m_axi_gmem_ARADDR,
        m_axi_gmem_ARID,
        m_axi_gmem_ARLEN,
        m_axi_gmem_ARSIZE,
        m_axi_gmem_ARBURST,
        m_axi_gmem_ARLOCK,
        m_axi_gmem_ARCACHE,
        m_axi_gmem_ARPROT,
        m_axi_gmem_ARQOS,
        m_axi_gmem_ARREGION,
        m_axi_gmem_ARUSER,
        m_axi_gmem_RVALID,
        m_axi_gmem_RREADY,
        m_axi_gmem_RDATA,
        m_axi_gmem_RLAST,
        m_axi_gmem_RID,
        m_axi_gmem_RUSER,
        m_axi_gmem_RRESP,
        m_axi_gmem_BVALID,
        m_axi_gmem_BREADY,
        m_axi_gmem_BRESP,
        m_axi_gmem_BID,
        m_axi_gmem_BUSER,
        s_axi_control_AWVALID,
        s_axi_control_AWREADY,
        s_axi_control_AWADDR,
        s_axi_control_WVALID,
        s_axi_control_WREADY,
        s_axi_control_WDATA,
        s_axi_control_WSTRB,
        s_axi_control_ARVALID,
        s_axi_control_ARREADY,
        s_axi_control_ARADDR,
        s_axi_control_RVALID,
        s_axi_control_RREADY,
        s_axi_control_RDATA,
        s_axi_control_RRESP,
        s_axi_control_BVALID,
        s_axi_control_BREADY,
        s_axi_control_BRESP,
        interrupt
);


Vivado HLS 2020.1

module DMA_pow2 (
        ap_clk,
        ap_rst_n,
        m_axi_gmem_AWVALID,
        m_axi_gmem_AWREADY,
        m_axi_gmem_AWADDR,
        m_axi_gmem_AWID,
        m_axi_gmem_AWLEN,
        m_axi_gmem_AWSIZE,
        m_axi_gmem_AWBURST,
        m_axi_gmem_AWLOCK,
        m_axi_gmem_AWCACHE,
        m_axi_gmem_AWPROT,
        m_axi_gmem_AWQOS,
        m_axi_gmem_AWREGION,
        m_axi_gmem_AWUSER,
        m_axi_gmem_WVALID,
        m_axi_gmem_WREADY,
        m_axi_gmem_WDATA,
        m_axi_gmem_WSTRB,
        m_axi_gmem_WLAST,
        m_axi_gmem_WID,
        m_axi_gmem_WUSER,
        m_axi_gmem_ARVALID,
        m_axi_gmem_ARREADY,
        m_axi_gmem_ARADDR,
        m_axi_gmem_ARID,
        m_axi_gmem_ARLEN,
        m_axi_gmem_ARSIZE,
        m_axi_gmem_ARBURST,
        m_axi_gmem_ARLOCK,
        m_axi_gmem_ARCACHE,
        m_axi_gmem_ARPROT,
        m_axi_gmem_ARQOS,
        m_axi_gmem_ARREGION,
        m_axi_gmem_ARUSER,
        m_axi_gmem_RVALID,
        m_axi_gmem_RREADY,
        m_axi_gmem_RDATA,
        m_axi_gmem_RLAST,
        m_axi_gmem_RID,
        m_axi_gmem_RUSER,
        m_axi_gmem_RRESP,
        m_axi_gmem_BVALID,
        m_axi_gmem_BREADY,
        m_axi_gmem_BRESP,
        m_axi_gmem_BID,
        m_axi_gmem_BUSER,
        s_axi_AXILiteS_AWVALID,
        s_axi_AXILiteS_AWREADY,
        s_axi_AXILiteS_AWADDR,
        s_axi_AXILiteS_WVALID,
        s_axi_AXILiteS_WREADY,
        s_axi_AXILiteS_WDATA,
        s_axi_AXILiteS_WSTRB,
        s_axi_AXILiteS_ARVALID,
        s_axi_AXILiteS_ARREADY,
        s_axi_AXILiteS_ARADDR,
        s_axi_AXILiteS_RVALID,
        s_axi_AXILiteS_RREADY,
        s_axi_AXILiteS_RDATA,
        s_axi_AXILiteS_RRESP,
        s_axi_AXILiteS_BVALID,
        s_axi_AXILiteS_BREADY,
        s_axi_AXILiteS_BRESP,
        interrupt
);


以前の”Vitis HLS 2020.1 と Vivado HLS 2019.2 の違い(AXI4 Master インターフェースでの offset=slave オプション時の扱いの違い)”では、AXI4 Lite インターフェースが 2 つに分かれてしまったが、今回の Vitis HLS 2020.1 では 1 つにまとまっている。その原因は引数のポートが AXI4 Lite インターフェースになっているかどうか?の違いがあるからかも知れない?

更に、AXI4 Lite インターフェースの Slave 機能でのアドレスマップを示す。

Vitis HLS 2020.1

//------------------------Address Info-------------------
// 0x00 : Control signals
//        bit 0  - ap_start (Read/Write/COH)
//        bit 1  - ap_done (Read/COR)
//        bit 2  - ap_idle (Read)
//        bit 3  - ap_ready (Read)
//        bit 7  - auto_restart (Read/Write)
//        others - reserved
// 0x04 : Global Interrupt Enable Register
//        bit 0  - Global Interrupt Enable (Read/Write)
//        others - reserved
// 0x08 : IP Interrupt Enable Register (Read/Write)
//        bit 0  - enable ap_done interrupt (Read/Write)
//        bit 1  - enable ap_ready interrupt (Read/Write)
//        others - reserved
// 0x0c : IP Interrupt Status Register (Read/TOW)
//        bit 0  - ap_done (COR/TOW)
//        bit 1  - ap_ready (COR/TOW)
//        others - reserved
// 0x10 : Data signal of ap_return
//        bit 31~0 - ap_return[31:0] (Read)
// 0x18 : Data signal of in_r
//        bit 31~0 - in_r[31:0] (Read/Write)
// 0x1c : Data signal of in_r
//        bit 31~0 - in_r[63:32] (Read/Write)
// 0x20 : reserved
// 0x24 : Data signal of out_r
//        bit 31~0 - out_r[31:0] (Read/Write)
// 0x28 : Data signal of out_r
//        bit 31~0 - out_r[63:32] (Read/Write)
// 0x2c : reserved
// (SC = Self Clear, COR = Clear on Read, TOW = Toggle on Write, COH = Clear on Handshake)


AXI4 Master のアドレスが 64 ビットになっているのが分かる。デフォルトで 64 ビットアドレスモードになっている。

Vivado HLS 2020.1

//------------------------Address Info-------------------
// 0x00 : Control signals
//        bit 0  - ap_start (Read/Write/COH)
//        bit 1  - ap_done (Read/COR)
//        bit 2  - ap_idle (Read)
//        bit 3  - ap_ready (Read)
//        bit 7  - auto_restart (Read/Write)
//        others - reserved
// 0x04 : Global Interrupt Enable Register
//        bit 0  - Global Interrupt Enable (Read/Write)
//        others - reserved
// 0x08 : IP Interrupt Enable Register (Read/Write)
//        bit 0  - Channel 0 (ap_done)
//        bit 1  - Channel 1 (ap_ready)
//        others - reserved
// 0x0c : IP Interrupt Status Register (Read/TOW)
//        bit 0  - Channel 0 (ap_done)
//        bit 1  - Channel 1 (ap_ready)
//        others - reserved
// 0x10 : Data signal of ap_return
//        bit 31~0 - ap_return[31:0] (Read)
// 0x18 : Data signal of in_r
//        bit 31~0 - in_r[31:0] (Read/Write)
// 0x1c : reserved
// 0x20 : Data signal of out_r
//        bit 31~0 - out_r[31:0] (Read/Write)
// 0x24 : reserved
// (SC = Self Clear, COR = Clear on Read, TOW = Toggle on Write, COH = Clear on Handshake)


AXI4 Master のアドレスは通常の 32 ビットモードになっている。


Analysis 画面を比較する。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_87_200915.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_88_200915.png


Vitis HLS 2020.1 で C コードの合成を行うと、パイプライン化だけではなく、入力の最適化もしてくれるようだ。驚いた。
  1. 2020年09月15日 04:51 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

FPGAの部屋のまとめサイトの更新(2020年9月14日)

FPGAの部屋のまとめサイトを更新しました。 VSCode, WSL2, Genesys_ZU, Alveo, ZynqBerryZero の各カテゴリを追加し、 2020 年 9 月 14 日までの記事を更新しました。
  1. 2020年09月14日 04:50 |
  2. その他のFPGAの話題
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その4 (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 で回路を作成し、動作させてみた。

ZYBO Z7-20 用の Vivado 2020.1 プロジェクトの multi_apuint_s_axilite_test プロジェクトを作成した。
Vitis_HLS_vs_Vivado_HLS_73_200912.png

multi_apuint IP を IP カタログに登録し、ブロックデザインに Add IP した。
Zynq Processing System も Add IP して、自動配線すると回路ができあがった。
Vitis_HLS_vs_Vivado_HLS_74_200912.png

Address Editor 画面を示す。
Vitis_HLS_vs_Vivado_HLS_75_200912.png

これでできあがったので、論理合成、インプリメンテーション、ビットストリームの生成を行って、成功した。
Vitis_HLS_vs_Vivado_HLS_76_200912.png

ハードウェアをエクスポートして、XSA ファイルを作成した。
Vitis を立ち上げて、作成した XSA ファイルを使って、プラットフォームとアプリケーション・プロジェクトを作成した。
アプリケーション・プロジェクトに multi_test.c ソフトウェアを追加した。
ビルドを行って成功した。
Vitis_HLS_vs_Vivado_HLS_77_200912.png

Vitis の Explorer の multi_apuint_axil を選択して、Run ボタンをクリックすると、ソフトウェアが起動して、シリアル・ターミナルにプロンプトが出た。
2 x 3 = 6 ができたので、前回、Vitis HLS 2020.1 で作成した 乗算 IP の動作に問題はないということが分かった。
Vitis_HLS_vs_Vivado_HLS_78_200912.png

これが動作するとすると、(普通のことだが) Vitis HLS 2020.1 と Vivado HLS 2020.1 の Export RTL (Vivado synthesis, place and routeにチェックを入れた時)のレポート機能にバグがあるのかも知れない?

最後に、multi_test.c を貼っておく。

// multi_test.c
// 2015/07/24 : by marsee
// multi_in0 の入力の時に999を入力すると終了する
// 2020/09/11 : Vitis HLS 2020.1 の IP 用にドライバの関数名を変更

#include <stdio.h>
#include "xmulti_apuint.h"
#include "xparameters.h"

int main(){
    XMulti_apuint XMluti_ap;
    XMulti_apuint_Config *XMulti_apPtr;
    int val;

    // Look Up the device configuration
    XMulti_apPtr = XMulti_apuint_LookupConfig(0);
    if (!XMulti_apPtr){
        fprintf(stderr, "XMulti_apuint configuration failed.\n");
        return(-1);
    }

    // Initialize the Device
    int Xlap_status = XMulti_apuint_CfgInitialize(&XMluti_ap, XMulti_apPtr);
    if (Xlap_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XMulti_apuint\n");
        return(-1);
    }

   while(1){
       printf("\n\rmulti_in0 = ");
       scanf("%d", &val);
       if(val == 999)
           break;
       XMulti_apuint_Set_multi_in0(&XMluti_ap, val);

       printf("\n\rmulti_in1 = ");
       scanf("%d", &val);
       XMulti_apuint_Set_multi_in1(&XMluti_ap, val);

       while(!XMulti_apuint_IsIdle(&XMluti_ap)) ;

       XMulti_apuint_Start(&XMluti_ap);

       while(!XMulti_apuint_IsDone(&XMluti_ap)) ;

       printf("\n\rmulti_out = %d\n\r", (int)XMulti_apuint_Get_multi_out_o(&XMluti_ap));
   }

   return(0);
}

  1. 2020年09月12日 04:13 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その4 (AXI4 Lite インターフェースの Slave 機能)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その3 (C/RTL 協調シミュレーション、Export RTL)”の続き。

簡単な乗算回路で、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は C/RTL 協調シミュレーションと Export RTL を比較した。今回は、AXI4 Lite インターフェースの Slave 機能を比較してみよう。

今回のソースコードは C コード部分では前回と同じだが、INTERFACE 指示子のオプションを s_axilite にすることで、AXI4 Lite インターフェースの Slave にする。
multi_apuint.cpp を示す。

// multi_apuint.cpp

#include <ap_int.h>

void multi_apuint(ap_uint<8> multi_in0, ap_uint<8> multi_in1,
        ap_uint<16> *multi_out){
#pragma HLS INTERFACE s_axilite port=multi_out
#pragma HLS INTERFACE s_axilite port=multi_in1
#pragma HLS INTERFACE s_axilite port=multi_in0
#pragma HLS INTERFACE s_axilite port=return
    *multi_out = multi_in0 * multi_in1;
}


Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_64_200911.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_65_200911.png


C コードの合成を行った。リソース使用量は Vivado HLS の方が少ない。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_68_200911.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_69_200911.png


生成された Verilog HDL ファイルを比較してみよう。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_70_200911.png

multi_apuint.v, multi_apuint_control_s_axi.v, multi_apuint_mul_8ns_8ns_16_1_1.v の 3 このファイルが合成されている。
AXI4 Lite インターフェースの信号名に s_axi_control_ が付けられている。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_71_200911.png

multi_apuint.v, multi_apuint_AXILiteS_s_axi.v の 2 このファイルが合成されている。
AXI4 Lite インターフェースの信号名に s_axi_AXILiteS_ が付けられている。


AXI4 Lite インターフェースのアドレスマップを比較する。

Vitis HLS 2020.1

//------------------------Address Info-------------------
// 0x00 : Control signals
//        bit 0  - ap_start (Read/Write/SC)
//        bit 1  - ap_done (Read/COR)
//        bit 2  - ap_idle (Read)
//        bit 3  - ap_ready (Read)
//        bit 7  - auto_restart (Read/Write)
//        others - reserved
// 0x04 : Global Interrupt Enable Register
//        bit 0  - Global Interrupt Enable (Read/Write)
//        others - reserved
// 0x08 : IP Interrupt Enable Register (Read/Write)
//        bit 0  - enable ap_done interrupt (Read/Write)
//        others - reserved
// 0x0c : IP Interrupt Status Register (Read/TOW)
//        bit 0  - ap_done (COR/TOW)
//        others - reserved
// 0x10 : Data signal of multi_in0
//        bit 31~0 - multi_in0[31:0] (Read/Write)
// 0x14 : reserved
// 0x18 : Data signal of multi_in1
//        bit 31~0 - multi_in1[31:0] (Read/Write)
// 0x1c : reserved
// 0x20 : Data signal of multi_out_i
//        bit 31~0 - multi_out_i[31:0] (Read/Write)
// 0x24 : reserved
// 0x28 : Data signal of multi_out_o
//        bit 31~0 - multi_out_o[31:0] (Read)
// 0x2c : Control signal of multi_out_o
//        bit 0  - multi_out_o_ap_vld (Read/COR)
//        others - reserved
// (SC = Self Clear, COR = Clear on Read, TOW = Toggle on Write, COH = Clear on Handshake)


Vivado HLS 2020.1

/------------------------Address Info-------------------
// 0x00 : Control signals
//        bit 0  - ap_start (Read/Write/SC)
//        bit 1  - ap_done (Read/COR)
//        bit 2  - ap_idle (Read)
//        bit 3  - ap_ready (Read)
//        bit 7  - auto_restart (Read/Write)
//        others - reserved
// 0x04 : Global Interrupt Enable Register
//        bit 0  - Global Interrupt Enable (Read/Write)
//        others - reserved
// 0x08 : IP Interrupt Enable Register (Read/Write)
//        bit 0  - Channel 0 (ap_done)
//        others - reserved
// 0x0c : IP Interrupt Status Register (Read/TOW)
//        bit 0  - Channel 0 (ap_done)
//        others - reserved
// 0x10 : Data signal of multi_in0_V
//        bit 7~0 - multi_in0_V[7:0] (Read/Write)
//        others  - reserved
// 0x14 : reserved
// 0x18 : Data signal of multi_in1_V
//        bit 7~0 - multi_in1_V[7:0] (Read/Write)
//        others  - reserved
// 0x1c : reserved
// 0x20 : Data signal of multi_out_V
//        bit 15~0 - multi_out_V[15:0] (Read)
//        others   - reserved
// 0x24 : Control signal of multi_out_V
//        bit 0  - multi_out_V_ap_vld (Read/COR)
//        others - reserved
// (SC = Self Clear, COR = Clear on Read, TOW = Toggle on Write, COH = Clear on Handshake


アドレスが異なる。Vitis HLS では信号名に _V が付かなくなったようだ。

Export RTL の結果を比較する。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_66_200911.png

DSP が 1 個だけなのはなぜだろうか?

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_67_200911.png

やはり DSP が 1 個だけだ。


これでは AXI4 Lite インターフェースの Slave 機能が消えているとしか思えない。 2020.1 のバグか?

それでは、同じソースコードで Vivado HLS 2019.2 で C コード合成を行ってから、Export RTL をやってみた。
Vitis_HLS_vs_Vivado_HLS_72_200911.png

LUT 、 FF が使われている。 Vivado HLS 2019.2 は大丈夫そうだ。
  1. 2020年09月11日 04:19 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vitis HLS 2020.1 の C/RTL 協調シミュレーション時の新機能2(Random Stall)

Vitis HLS 2020.1 の C/RTL 協調シミュレーション時の新機能1(Wave Debug)”の続き。

前回は、Vitis HLS 2020.1 の新機能の内の Wave Debug を紹介した。今回は、Random Stall を紹介する。
Random Stall は UVM のランダム検証(UVM 知らないので、良く分からないが)を使っているらしい? UVM のメッセージが出てくる。機能としては、データ転送中に適当に Wait を入れて、データ転送が正しいかどうか?を確認しているようだ?

まずは、ソースコードは”Vivado HLS 2020.1 vs Vitis HLS 2020.1 (プロジェクトの作成)”に指示子を追加した。
テストベンチは”Vivado HLS 2020.1 vs Vitis HLS 2020.1 (プロジェクトの作成)”のテストベンチコードを使用している。
Vitis_HLS_vs_Vivado_HLS_46_200910.png

// multi_apuint.cpp

#include <ap_int.h>

void multi_apuint(ap_uint<8> multi_in0, ap_uint<8> multi_in1,
        ap_uint<16> *multi_out){
#pragma HLS PIPELINE
#pragma HLS INTERFACE ap_hs register port=multi_out
#pragma HLS INTERFACE ap_hs register port=multi_in1
#pragma HLS INTERFACE ap_hs register port=multi_in0
    *multi_out = multi_in0 * multi_in1;
}


Run C/RTL Cosimulation ボタンをクリックして C/RTL 協調シミュレーションを行った。
C/RTL Co-simulation Dialog で Dump Trace を all に変更する。
Vitis_HLS_vs_Vivado_HLS_50_200910.png

C/RTL 協調シミュレーションの結果を示す。
Vitis_HLS_vs_Vivado_HLS_47_200910.png

C/RTL 協調シミュレーションのログを示す。

Starting C/RTL cosimulation ...
/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vitis/2020.1/bin/vitis_hls /media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/cosim.tcl
INFO: [HLS 200-10] Running '/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vitis/2020.1/bin/unwrapped/lnx64.o/vitis_hls'
INFO: [HLS 200-10] For user 'masaaki' on host 'masaaki-H110M4-M01' (Linux_x86_64 version 4.15.0-115-generic) on Wed Sep 09 20:41:00 JST 2020
INFO: [HLS 200-10] On os Ubuntu 18.04.5 LTS
INFO: [HLS 200-10] In directory '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar'
WARNING: [HLS 200-40] Environment variable 'C_INCLUDE_PATH' is set to :/usr/local/cuda/include.
Sourcing Tcl script '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/cosim.tcl'
INFO: [HLS 200-10] Opening project '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint'.
INFO: [HLS 200-10] Adding design file 'multi_apuint/multi_apuint.cpp' to the project
INFO: [HLS 200-10] Adding test bench file 'multi_apuint/multi_apuint_tb.cpp' to the project
INFO: [HLS 200-10] Opening solution '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1'.
INFO: [SYN 201-201] Setting up clock 'default' with a period of 10ns.
INFO: [HLS 200-10] Setting target device to 'xc7z020-clg400-1'
INFO: [HLS 200-1505] Using flow_target 'vivado'
Resolution: For help on HLS 200-1505 see www.xilinx.com/html_docs/xilinx2020_1/hls-guidance/200-1505.html
INFO: [HLS 200-1464] Running solution command: config_export -format=ip_catalog
INFO: [HLS 200-1464] Running solution command: config_export -rtl=verilog
INFO: [SYN 201-201] Setting up clock 'default' with a period of 10ns.
INFO: [COSIM 212-47] Using XSIM for RTL simulation.
INFO: [COSIM 212-14] Instrumenting C test bench ...
   Build using "/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vivado/2020.1/tps/lnx64/gcc-6.2.0/bin/g++"
   Compiling multi_apuint_tb.cpp_pre.cpp.tb.cpp
   Compiling apatb_multi_apuint.cpp
   Compiling multi_apuint.cpp_pre.cpp.tb.cpp
   Generating cosim.tv.exe
INFO: [COSIM 212-302] Starting C TB testing ... 
multi_out = 0
multi_out = 2
multi_out = 6
multi_out = 12
multi_out = 20
multi_out = 30
multi_out = 42
multi_out = 56
multi_out = 72
multi_out = 90
INFO: [COSIM 212-333] Generating C post check test bench ...
INFO: [COSIM 212-12] Generating RTL test bench ...
INFO: [COSIM 212-1] *** C/RTL co-simulation file generation completed. ***
INFO: [COSIM 212-323] Starting verilog simulation. 
INFO: [COSIM 212-15] Starting XSIM ...
Vivado Simulator 2020.1
Copyright 1986-1999, 2001-2020 Xilinx, Inc. All Rights Reserved.
Running: /media/masaaki/Ubuntu_Disk/tools/Xilinx/Vivado/2020.1/patches/AR75369_vivado_2020_1_preliminary_rev1/vivado/bin/unwrapped/lnx64.o/xelab xil_defaultlib.apatb_multi_apuint_top glbl -prj multi_apuint.prj -L smartconnect_v1_0 -L axi_protocol_checker_v1_1_12 -L axi_protocol_checker_v1_1_13 -L axis_protocol_checker_v1_1_11 -L axis_protocol_checker_v1_1_12 -L xil_defaultlib -L unisims_ver -L xpm --lib ieee_proposed=./ieee_proposed -s multi_apuint -debug wave 
Multi-threading is on. Using 2 slave threads.
WARNING: [XSIM 43-3431] One or more environment variables have been detected which affect the operation of the C compiler. These are typically not set in standard installations and are not tested by Xilinx, however they may be appropriate for your system, so the flow will attempt to continue.  If errors occur, try running xelab with the "-mt off -v 1" switches to see more information from the C compiler. The following environment variables have been detected:
    C_INCLUDE_PATH
    LIBRARY_PATH
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/glbl.v" into library work
INFO: [VRFC 10-311] analyzing module glbl
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.autotb.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module apatb_multi_apuint_top
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module multi_apuint
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0
INFO: [VRFC 10-311] analyzing module multi_apuint_mul_8ns_8ns_16_1_1
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module regslice_both
INFO: [VRFC 10-311] analyzing module regslice_forward
INFO: [VRFC 10-311] analyzing module regslice_reverse
INFO: [VRFC 10-311] analyzing module regslice_both_w1
INFO: [VRFC 10-311] analyzing module regslice_forward_w1
INFO: [VRFC 10-311] analyzing module regslice_reverse_w1
INFO: [VRFC 10-311] analyzing module ibuf
INFO: [VRFC 10-311] analyzing module obuf
Starting static elaboration
Pass Through NonSizing Optimizer
Completed static elaboration
Starting simulation data flow analysis
Completed simulation data flow analysis
Time Resolution for simulation is 1ps
Compiling module xil_defaultlib.multi_apuint_mul_8ns_8ns_16_1_1_...
Compiling module xil_defaultlib.multi_apuint_mul_8ns_8ns_16_1_1(...
Compiling module xil_defaultlib.obuf(W=9)
Compiling module xil_defaultlib.regslice_forward(DataWidth=8)
Compiling module xil_defaultlib.obuf(W=17)
Compiling module xil_defaultlib.regslice_forward(DataWidth=16)
Compiling module xil_defaultlib.multi_apuint
Compiling module xil_defaultlib.apatb_multi_apuint_top
Compiling module work.glbl
Built simulation snapshot multi_apuint


****** Webtalk v2020.1_AR75369 (64-bit)
  **** SW Build 2902540 on Wed May 27 19:54:35 MDT 2020
  **** IP Build 2902112 on Wed May 27 22:43:36 MDT 2020
    ** Copyright 1986-2020 Xilinx, Inc. All Rights Reserved.


source /media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/xsim.dir/multi_apuint/webtalk/xsim_webtalk.tcl -notrace
INFO: [Common 17-206] Exiting Webtalk at Wed Sep  9 20:41:13 2020...


****** xsim v2020.1_AR75369 (64-bit)
  **** SW Build 2902540 on Wed May 27 19:54:35 MDT 2020
  **** IP Build 2902112 on Wed May 27 22:43:36 MDT 2020
    ** Copyright 1986-2020 Xilinx, Inc. All Rights Reserved.


source xsim.dir/multi_apuint/xsim_script.tcl
# xsim {multi_apuint} -autoloadwcfg -tclbatch {multi_apuint.tcl}
Vivado Simulator 2020.1
Time resolution is 1 ps
source multi_apuint.tcl
## log_wave -r /
WARNING: [Simtcl 6-197] One or more HDL objects could not be logged because of object type or size limitations.  To see details please rerun the command with -verbose (-v).
## set designtopgroup [add_wave_group "Design Top Signals"]
## set coutputgroup [add_wave_group "C Outputs" -into $designtopgroup]
## set multi_out_group [add_wave_group multi_out(wire) -into $coutputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out_ap_vld -into $multi_out_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out -into $multi_out_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out_ap_ack -into $multi_out_group -color #ffff00 -radix hex
## set cinputgroup [add_wave_group "C Inputs" -into $designtopgroup]
## set multi_in0_group [add_wave_group multi_in0(wire) -into $cinputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0_ap_ack -into $multi_in0_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0 -into $multi_in0_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0_ap_vld -into $multi_in0_group -color #ffff00 -radix hex
## set multi_in1_group [add_wave_group multi_in1(wire) -into $cinputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1_ap_ack -into $multi_in1_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1 -into $multi_in1_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1_ap_vld -into $multi_in1_group -color #ffff00 -radix hex
## set blocksiggroup [add_wave_group "Block-level IO Handshake" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_start -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_done -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_idle -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_ready -into $blocksiggroup
## set resetgroup [add_wave_group "Reset" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_rst -into $resetgroup
## set clockgroup [add_wave_group "Clock" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_clk -into $clockgroup
## set testbenchgroup [add_wave_group "Test Bench Signals"]
## set tbinternalsiggroup [add_wave_group "Internal Signals" -into $testbenchgroup]
## set tb_simstatus_group [add_wave_group "Simulation Status" -into $tbinternalsiggroup]
## set tb_portdepth_group [add_wave_group "Port Depth" -into $tbinternalsiggroup]
## add_wave /apatb_multi_apuint_top/AUTOTB_TRANSACTION_NUM -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/ready_cnt -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/done_cnt -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_in0 -into $tb_portdepth_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_in1 -into $tb_portdepth_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_out -into $tb_portdepth_group -radix hex
## set tbcoutputgroup [add_wave_group "C Outputs" -into $testbenchgroup]
## set tb_multi_out_group [add_wave_group multi_out(wire) -into $tbcoutputgroup]
## add_wave /apatb_multi_apuint_top/multi_out_ap_vld -into $tb_multi_out_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_out -into $tb_multi_out_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_out_ap_ack -into $tb_multi_out_group -color #ffff00 -radix hex
## set tbcinputgroup [add_wave_group "C Inputs" -into $testbenchgroup]
## set tb_multi_in0_group [add_wave_group multi_in0(wire) -into $tbcinputgroup]
## add_wave /apatb_multi_apuint_top/multi_in0_ap_ack -into $tb_multi_in0_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_in0 -into $tb_multi_in0_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_in0_ap_vld -into $tb_multi_in0_group -color #ffff00 -radix hex
## set tb_multi_in1_group [add_wave_group multi_in1(wire) -into $tbcinputgroup]
## add_wave /apatb_multi_apuint_top/multi_in1_ap_ack -into $tb_multi_in1_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_in1 -into $tb_multi_in1_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_in1_ap_vld -into $tb_multi_in1_group -color #ffff00 -radix hex
## save_wave_config multi_apuint.wcfg
## run all
////////////////////////////////////////////////////////////////////////////////////
// Inter-Transaction Progress: Completed Transaction / Total Transaction
// Intra-Transaction Progress: Measured Latency / Latency Estimation * 100%
//
// RTL Simulation : "Inter-Transaction Progress" ["Intra-Transaction Progress"] @ "Simulation Time"
////////////////////////////////////////////////////////////////////////////////////
// RTL Simulation : 0 / 10 [0.00%] @ "1125000"
// RTL Simulation : 1 / 10 [50.00%] @ "1165000"
// RTL Simulation : 2 / 10 [50.00%] @ "1175000"
// RTL Simulation : 3 / 10 [50.00%] @ "1185000"
// RTL Simulation : 4 / 10 [50.00%] @ "1195000"
// RTL Simulation : 5 / 10 [50.00%] @ "1205000"
// RTL Simulation : 6 / 10 [50.00%] @ "1215000"
// RTL Simulation : 7 / 10 [50.00%] @ "1225000"
// RTL Simulation : 8 / 10 [50.00%] @ "1235000"
// RTL Simulation : 9 / 10 [50.00%] @ "1245000"
// RTL Simulation : 10 / 10 [100.00%] @ "1255000"
////////////////////////////////////////////////////////////////////////////////////
$finish called at time : 1295 ns : File "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.autotb.v" Line 382
## quit
INFO: [Common 17-206] Exiting xsim at Wed Sep  9 20:41:23 2020...
INFO: [COSIM 212-316] Starting C post checking ...
multi_out = 0
multi_out = 2
multi_out = 6
multi_out = 12
multi_out = 20
multi_out = 30
multi_out = 42
multi_out = 56
multi_out = 72
multi_out = 90
INFO: [COSIM 212-1000] *** C/RTL co-simulation finished: PASS ***
Finished C/RTL cosimulation.


C/RTL 協調シミュレーションの全体波形を示す。
Vitis_HLS_vs_Vivado_HLS_48_200910.png

拡大波形を示す。
Vitis_HLS_vs_Vivado_HLS_49_200910.png

データ転送に Wait は入っていない。


次に、Run C/RTL Cosimulation ボタンをクリックして C/RTL 協調シミュレーションを行った。
C/RTL Co-simulation Dialog で Dump Trace を all に、Random Stall のチェックを入れた。
Vitis_HLS_vs_Vivado_HLS_51_200910.png

これで、C/RTL 協調シミュレーションを行った。結果を示す。
Vitis_HLS_vs_Vivado_HLS_52_200910.png

Latency の avg は 3 クロック、 max は 6 クロック、 Interval の max が 3 クロックになった。

ログを示す。

Starting C/RTL cosimulation ...
/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vitis/2020.1/bin/vitis_hls /media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/cosim.tcl
INFO: [HLS 200-10] Running '/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vitis/2020.1/bin/unwrapped/lnx64.o/vitis_hls'
INFO: [HLS 200-10] For user 'masaaki' on host 'masaaki-H110M4-M01' (Linux_x86_64 version 4.15.0-115-generic) on Thu Sep 10 03:39:27 JST 2020
INFO: [HLS 200-10] On os Ubuntu 18.04.5 LTS
INFO: [HLS 200-10] In directory '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar'
WARNING: [HLS 200-40] Environment variable 'C_INCLUDE_PATH' is set to :/usr/local/cuda/include.
Sourcing Tcl script '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/cosim.tcl'
INFO: [HLS 200-10] Opening project '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint'.
INFO: [HLS 200-10] Adding design file 'multi_apuint/multi_apuint.cpp' to the project
INFO: [HLS 200-10] Adding test bench file 'multi_apuint/multi_apuint_tb.cpp' to the project
INFO: [HLS 200-10] Opening solution '/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1'.
INFO: [SYN 201-201] Setting up clock 'default' with a period of 10ns.
INFO: [HLS 200-10] Setting target device to 'xc7z020-clg400-1'
INFO: [HLS 200-1505] Using flow_target 'vivado'
Resolution: For help on HLS 200-1505 see www.xilinx.com/html_docs/xilinx2020_1/hls-guidance/200-1505.html
INFO: [HLS 200-1464] Running solution command: config_export -format=ip_catalog
INFO: [HLS 200-1464] Running solution command: config_export -rtl=verilog
INFO: [SYN 201-201] Setting up clock 'default' with a period of 10ns.
INFO: [COSIM 212-47] Using XSIM for RTL simulation.
INFO: [COSIM 212-14] Instrumenting C test bench ...
   Build using "/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vivado/2020.1/tps/lnx64/gcc-6.2.0/bin/g++"
   Compiling multi_apuint_tb.cpp_pre.cpp.tb.cpp
   Compiling apatb_multi_apuint.cpp
   Compiling multi_apuint.cpp_pre.cpp.tb.cpp
   Generating cosim.tv.exe
INFO: [COSIM 212-302] Starting C TB testing ... 
multi_out = 0
multi_out = 2
multi_out = 6
multi_out = 12
multi_out = 20
multi_out = 30
multi_out = 42
multi_out = 56
multi_out = 72
multi_out = 90
INFO: [COSIM 212-333] Generating C post check test bench ...
INFO: [COSIM 212-12] Generating RTL test bench ...
apatb_multi_apuint_top.AESL_clock 0 apatb_multi_apuint_top.AESL_reset 1
INFO: [COSIM 212-1] *** C/RTL co-simulation file generation completed. ***
INFO: [COSIM 212-323] Starting verilog simulation. 
INFO: [COSIM 212-15] Starting XSIM ...
Vivado Simulator 2020.1
Copyright 1986-1999, 2001-2020 Xilinx, Inc. All Rights Reserved.
Running: /media/masaaki/Ubuntu_Disk/tools/Xilinx/Vivado/2020.1/patches/AR75369_vivado_2020_1_preliminary_rev1/vivado/bin/unwrapped/lnx64.o/xelab xil_defaultlib.apatb_multi_apuint_top xil_defaultlib.glbl -prj multi_apuint.prj -L smartconnect_v1_0 -L axi_protocol_checker_v1_1_12 -L axi_protocol_checker_v1_1_13 -L axis_protocol_checker_v1_1_11 -L axis_protocol_checker_v1_1_12 -L xil_defaultlib -L unisims_ver -L xpm --lib ieee_proposed=./ieee_proposed -L uvm -relax -i ./svr -i ./svtb -i ./file_agent -i ./multi_apuint_subsystem -s multi_apuint -debug wave 
Multi-threading is on. Using 2 slave threads.
WARNING: [XSIM 43-3431] One or more environment variables have been detected which affect the operation of the C compiler. These are typically not set in standard installations and are not tested by Xilinx, however they may be appropriate for your system, so the flow will attempt to continue.  If errors occur, try running xelab with the "-mt off -v 1" switches to see more information from the C compiler. The following environment variables have been detected:
    C_INCLUDE_PATH
    LIBRARY_PATH
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/glbl.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module glbl
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.autotb.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module apatb_multi_apuint_top
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module multi_apuint
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0
INFO: [VRFC 10-311] analyzing module multi_apuint_mul_8ns_8ns_16_1_1
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module regslice_both
INFO: [VRFC 10-311] analyzing module regslice_forward
INFO: [VRFC 10-311] analyzing module regslice_reverse
INFO: [VRFC 10-311] analyzing module regslice_both_w1
INFO: [VRFC 10-311] analyzing module regslice_forward_w1
INFO: [VRFC 10-311] analyzing module regslice_reverse_w1
INFO: [VRFC 10-311] analyzing module ibuf
INFO: [VRFC 10-311] analyzing module obuf
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/file_agent/file_agent_pkg.sv" into library xil_defaultlib
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svr/svr_pkg.sv" into library xil_defaultlib
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svr/svr_if.sv" into library xil_defaultlib
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_subsystem/multi_apuint_subsystem_pkg.sv" into library xil_defaultlib
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/misc_interface.sv" into library xil_defaultlib
INFO: [VRFC 10-2263] Analyzing SystemVerilog file "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/sv_module_top.sv" into library xil_defaultlib
INFO: [VRFC 10-311] analyzing module sv_module_top
Starting static elaboration
Pass Through NonSizing Optimizer
WARNING: [VRFC 10-3597] non-void function 'write_one_elem' called as a task without void casting [./file_agent/mem_model.sv:143]
WARNING: [VRFC 10-3597] non-void function 'write_elems' called as a task without void casting [./file_agent/mem_model.sv:153]
WARNING: [VRFC 10-3597] non-void function 'read_elems' called as a task without void casting [./file_agent/mem_model.sv:157]
WARNING: [VRFC 10-3597] non-void function 'read_one_elem' called as a task without void casting [./file_agent/mem_model.sv:169]
WARNING: [VRFC 10-3597] non-void function 'read_one_elem' called as a task without void casting [./file_agent/mem_model.sv:190]
WARNING: [VRFC 10-3597] non-void function 'init' called as a task without void casting [./svr/svr_object_global.svh:59]
Completed static elaboration
Starting simulation data flow analysis
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/sv_module_top.sv" Line 1. Module $unit_sv_module_top_sv has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.autotb.v" Line 26. Module apatb_multi_apuint_top has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.v" Line 10. Module multi_apuint has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" Line 16. Module multi_apuint_mul_8ns_8ns_16_1_1(ID=1,NUM_STAGE=1,din0_WIDTH=8,din1_WIDTH=8,dout_WIDTH=16) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" Line 8. Module multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0 has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=8) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=9) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=8) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=9) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=16) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=17) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/sv_module_top.sv" Line 22. Module sv_module_top has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/misc_interface.sv" Line 8. Module misc_interface has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.autotb.v" Line 26. Module apatb_multi_apuint_top has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint.v" Line 10. Module multi_apuint has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" Line 16. Module multi_apuint_mul_8ns_8ns_16_1_1(ID=1,NUM_STAGE=1,din0_WIDTH=8,din1_WIDTH=8,dout_WIDTH=16) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/multi_apuint_mul_8ns_8ns_16_1_1.v" Line 8. Module multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0 has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=8) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=9) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=8) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=9) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 122. Module regslice_forward(DataWidth=16) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/regslice_core.v" Line 460. Module obuf(W=17) has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/sv_module_top.sv" Line 22. Module sv_module_top has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/svtb/misc_interface.sv" Line 8. Module misc_interface has a timescale but at least one module in design doesn't have timescale.
WARNING: [XSIM 43-4100] "/media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/glbl.v" Line 6. Module glbl has a timescale but at least one module in design doesn't have timescale.
Completed simulation data flow analysis
Time Resolution for simulation is 1ps
Compiling package uvm.uvm_pkg
Compiling package std.std
Compiling package xil_defaultlib.svr_pkg
Compiling package xil_defaultlib.file_agent_pkg
WARNING: [XSIM 43-3373] "./file_agent/file_read_agent.sv" Line 424. System function $sscanf is used as system task. This system function should have a LHS e.g. x=$sscanf().
Compiling package xil_defaultlib.$unit_sv_module_top_sv
Compiling package xil_defaultlib.multi_apuint_subsystem_pkg
Compiling module xil_defaultlib.multi_apuint_mul_8ns_8ns_16_1_1_...
Compiling module xil_defaultlib.multi_apuint_mul_8ns_8ns_16_1_1(...
Compiling module xil_defaultlib.obuf(W=9)
Compiling module xil_defaultlib.regslice_forward(DataWidth=8)
Compiling module xil_defaultlib.obuf(W=17)
Compiling module xil_defaultlib.regslice_forward(DataWidth=16)
Compiling module xil_defaultlib.multi_apuint
Compiling module xil_defaultlib.misc_interface
Compiling module xil_defaultlib.svr_if(DATA_WIDTH=8)
Compiling module xil_defaultlib.svr_if(DATA_WIDTH=16)
Compiling module xil_defaultlib.sv_module_top
Compiling module xil_defaultlib.apatb_multi_apuint_top
Compiling module xil_defaultlib.glbl
Built simulation snapshot multi_apuint


****** Webtalk v2020.1_AR75369 (64-bit)
  **** SW Build 2902540 on Wed May 27 19:54:35 MDT 2020
  **** IP Build 2902112 on Wed May 27 22:43:36 MDT 2020
    ** Copyright 1986-2020 Xilinx, Inc. All Rights Reserved.


source /media/masaaki/Ubuntu_Disk/Vitis_HLS/Tsukuba_seminar/multi_apuint/solution1/sim/verilog/xsim.dir/multi_apuint/webtalk/xsim_webtalk.tcl -notrace
INFO: [Common 17-206] Exiting Webtalk at Thu Sep 10 03:40:32 2020...


****** xsim v2020.1_AR75369 (64-bit)
  **** SW Build 2902540 on Wed May 27 19:54:35 MDT 2020
  **** IP Build 2902112 on Wed May 27 22:43:36 MDT 2020
    ** Copyright 1986-2020 Xilinx, Inc. All Rights Reserved.


source xsim.dir/multi_apuint/xsim_script.tcl
# xsim {multi_apuint} -testplusarg UVM_VERBOSITY=UVM_LOW -testplusarg UVM_TESTNAME=multi_apuint_test_lib -testplusarg UVM_TIMEOUT=20000000000000 -autoloadwcfg -tclbatch {multi_apuint.tcl}
Vivado Simulator 2020.1
Time resolution is 1 ps
source multi_apuint.tcl
## log_wave -r /
## set designtopgroup [add_wave_group "Design Top Signals"]
## set coutputgroup [add_wave_group "C Outputs" -into $designtopgroup]
## set multi_out_group [add_wave_group multi_out(wire) -into $coutputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out_ap_vld -into $multi_out_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out -into $multi_out_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_out_ap_ack -into $multi_out_group -color #ffff00 -radix hex
## set cinputgroup [add_wave_group "C Inputs" -into $designtopgroup]
## set multi_in0_group [add_wave_group multi_in0(wire) -into $cinputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0_ap_ack -into $multi_in0_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0 -into $multi_in0_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in0_ap_vld -into $multi_in0_group -color #ffff00 -radix hex
## set multi_in1_group [add_wave_group multi_in1(wire) -into $cinputgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1_ap_ack -into $multi_in1_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1 -into $multi_in1_group -radix hex
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/multi_in1_ap_vld -into $multi_in1_group -color #ffff00 -radix hex
## set blocksiggroup [add_wave_group "Block-level IO Handshake" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_start -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_done -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_idle -into $blocksiggroup
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_ready -into $blocksiggroup
## set resetgroup [add_wave_group "Reset" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_rst -into $resetgroup
## set clockgroup [add_wave_group "Clock" -into $designtopgroup]
## add_wave /apatb_multi_apuint_top/AESL_inst_multi_apuint/ap_clk -into $clockgroup
## set testbenchgroup [add_wave_group "Test Bench Signals"]
## set tbinternalsiggroup [add_wave_group "Internal Signals" -into $testbenchgroup]
## set tb_simstatus_group [add_wave_group "Simulation Status" -into $tbinternalsiggroup]
## set tb_portdepth_group [add_wave_group "Port Depth" -into $tbinternalsiggroup]
## add_wave /apatb_multi_apuint_top/AUTOTB_TRANSACTION_NUM -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/ready_cnt -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/done_cnt -into $tb_simstatus_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_in0 -into $tb_portdepth_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_in1 -into $tb_portdepth_group -radix hex
## add_wave /apatb_multi_apuint_top/LENGTH_multi_out -into $tb_portdepth_group -radix hex
## set tbcoutputgroup [add_wave_group "C Outputs" -into $testbenchgroup]
## set tb_multi_out_group [add_wave_group multi_out(wire) -into $tbcoutputgroup]
## add_wave /apatb_multi_apuint_top/multi_out_ap_vld -into $tb_multi_out_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_out -into $tb_multi_out_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_out_ap_ack -into $tb_multi_out_group -color #ffff00 -radix hex
## set tbcinputgroup [add_wave_group "C Inputs" -into $testbenchgroup]
## set tb_multi_in0_group [add_wave_group multi_in0(wire) -into $tbcinputgroup]
## add_wave /apatb_multi_apuint_top/multi_in0_ap_ack -into $tb_multi_in0_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_in0 -into $tb_multi_in0_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_in0_ap_vld -into $tb_multi_in0_group -color #ffff00 -radix hex
## set tb_multi_in1_group [add_wave_group multi_in1(wire) -into $tbcinputgroup]
## add_wave /apatb_multi_apuint_top/multi_in1_ap_ack -into $tb_multi_in1_group -color #ffff00 -radix hex
## add_wave /apatb_multi_apuint_top/multi_in1 -into $tb_multi_in1_group -radix hex
## add_wave /apatb_multi_apuint_top/multi_in1_ap_vld -into $tb_multi_in1_group -color #ffff00 -radix hex
## save_wave_config multi_apuint.wcfg
## run all
UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(18601) @ 0: reporter [UVM/RELNOTES] 
      (Specify +UVM_NO_RELNOTES to turn off this notice)
  with `UVM_OBJECT_DO_NOT_NEED_CONSTRUCTOR undefined.


  You are using a version of the UVM library that has been compiled
  with `UVM_NO_DEPRECATED undefined.


  You are using a version of the UVM library that has been compiled


  ***********       IMPORTANT RELEASE NOTES         ************
----------------------------------------------------------------
(C) 2013-2014 NVIDIA Corporation
(C) 2011-2013 Cypress Semiconductor Corp.
(C) 2006-2014 Synopsys, Inc.
(C) 2007-2014 Cadence Design Systems, Inc.
(C) 2007-2014 Mentor Graphics Corporation


----------------------------------------------------------------


UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(18648) @ 0: reporter [NO_DPI_TSTNAME] UVM_NO_DPI defined--getting UVM_TESTNAME directly, without DPI
UVM_INFO @ 0: reporter [RNTST] Running test multi_apuint_test_lib...
UVM_INFO ./svtb/multi_apuint_test_lib.sv(29) @ 0: uvm_test_top [uvm_test_top] build_phase done
UVM_INFO ./multi_apuint_subsystem/multi_apuint_env.sv(138) @ 0: uvm_test_top.top_env [uvm_test_top.top_env] set reference model by uvm_config_db
UVM_INFO ./multi_apuint_subsystem/multi_apuint_env.sv(145) @ 0: uvm_test_top.top_env [uvm_test_top.top_env] build_phase done
UVM_INFO ./svr/svr_env.sv(27) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0 [uvm_test_top.top_env.env_master_svr_multi_in0] build_phase is called
UVM_INFO ./svr/svr_master_sequencer.sv(12) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.sqr [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.sqr] new is called
UVM_INFO ./svr/svr_master_driver.sv(15) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv] new is called
UVM_INFO ./svr/svr_master_monitor.sv(34) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.mon [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.mon] new is called
UVM_INFO ./svr/svr_master_driver.sv(25) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv] build_phase is called
UVM_INFO ./svr/svr_master_monitor.sv(41) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.mon [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.mon] build_phase is called
UVM_INFO ./svr/svr_env.sv(27) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1 [uvm_test_top.top_env.env_master_svr_multi_in1] build_phase is called
UVM_INFO ./svr/svr_master_sequencer.sv(12) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.sqr [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.sqr] new is called
UVM_INFO ./svr/svr_master_driver.sv(15) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv] new is called
UVM_INFO ./svr/svr_master_monitor.sv(34) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.mon [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.mon] new is called
UVM_INFO ./svr/svr_master_driver.sv(25) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv] build_phase is called
UVM_INFO ./svr/svr_master_monitor.sv(41) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.mon [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.mon] build_phase is called
UVM_INFO ./svr/svr_env.sv(27) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out [uvm_test_top.top_env.env_slave_svr_multi_out] build_phase is called
UVM_INFO ./svr/svr_slave_sequencer.sv(12) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.sqr [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.sqr] new is called
UVM_INFO ./svr/svr_slave_driver.sv(15) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv] new is called
UVM_INFO ./svr/svr_slave_monitor.sv(34) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon] new is called
UVM_INFO ./svr/svr_slave_driver.sv(25) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv] build_phase is called
UVM_INFO ./svr/svr_slave_monitor.sv(41) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon] build_phase is called
UVM_INFO ./multi_apuint_subsystem/multi_apuint_env.sv(163) @ 0: uvm_test_top.top_env [uvm_test_top.top_env] connect phase done
UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(18752) @ 0: reporter [UVMTOP] UVM testbench topology:
----------------------------------------------------------------------------------------------------------------
Name                                               Type                                   Size  Value           
----------------------------------------------------------------------------------------------------------------
uvm_test_top                                       multi_apuint_test_lib                  -     @353            
  top_env                                          multi_apuint_env                       -     @366            
    env_master_svr_multi_in0                       uvm_env                                -     @389            
      m_agt                                        uvm_agent                              -     @621            
        drv                                        uvm_driver #(REQ,RSP)                  -     @771            
          rsp_port                                 uvm_analysis_port                      -     @790            
          seq_item_port                            uvm_seq_item_pull_port                 -     @780            
        mon                                        uvm_monitor                            -     @802            
          item_collect_port                        uvm_analysis_port                      -     @819            
        sqr                                        uvm_sequencer                          -     @632            
          rsp_export                               uvm_analysis_export                    -     @641            
          seq_item_export                          uvm_seq_item_pull_imp                  -     @759            
          arbitration_queue                        array                                  0     -               
          lock_queue                               array                                  0     -               
          num_last_reqs                            integral                               32    'd1             
          num_last_rsps                            integral                               32    'd1             
    env_master_svr_multi_in1                       uvm_env                                -     @402            
      m_agt                                        uvm_agent                              -     @839            
        drv                                        uvm_driver #(REQ,RSP)                  -     @989            
          rsp_port                                 uvm_analysis_port                      -     @1008           
          seq_item_port                            uvm_seq_item_pull_port                 -     @998            
        mon                                        uvm_monitor                            -     @1020           
          item_collect_port                        uvm_analysis_port                      -     @1037           
        sqr                                        uvm_sequencer                          -     @850            
          rsp_export                               uvm_analysis_export                    -     @859            
          seq_item_export                          uvm_seq_item_pull_imp                  -     @977            
          arbitration_queue                        array                                  0     -               
          lock_queue                               array                                  0     -               
          num_last_reqs                            integral                               32    'd1             
          num_last_rsps                            integral                               32    'd1             
    env_slave_svr_multi_out                        uvm_env                                -     @412            
      s_agt                                        uvm_agent                              -     @1057           
        drv                                        uvm_driver #(REQ,RSP)                  -     @1207           
          rsp_port                                 uvm_analysis_port                      -     @1226           
          seq_item_port                            uvm_seq_item_pull_port                 -     @1216           
        mon                                        uvm_monitor                            -     @1238           
          item_collect_port                        uvm_analysis_port                      -     @1255           
        sqr                                        uvm_sequencer                          -     @1068           
          rsp_export                               uvm_analysis_export                    -     @1077           
          seq_item_export                          uvm_seq_item_pull_imp                  -     @1195           
          arbitration_queue                        array                                  0     -               
          lock_queue                               array                                  0     -               
          num_last_reqs                            integral                               32    'd1             
          num_last_rsps                            integral                               32    'd1             
    multi_apuint_virtual_sqr                       multi_apuint_virtual_sequencer         -     @479            
      rsp_export                                   uvm_analysis_export                    -     @488            
      seq_item_export                              uvm_seq_item_pull_imp                  -     @606            
      arbitration_queue                            array                                  0     -               
      lock_queue                                   array                                  0     -               
      num_last_reqs                                integral                               32    'd1             
      num_last_rsps                                integral                               32    'd1             
    refm                                           multi_apuint_reference_model           -     @425            
      trans_num_idx                                integral                               32    'h0             
    subsys_mon                                     multi_apuint_subsystem_monitor         -     @440            
      scbd                                         multi_apuint_scoreboard                -     @1282           
        refm                                       multi_apuint_reference_model           -     @425            
          trans_num_idx                            integral                               32    'h0             
        TVOUT_transaction_size_queue               da(integral)                           0     -               
        file_wr_port_multi_out_multi_out           <unknown>                              -     @1292           
          TV_FILE                                  string                                 0     ""              
          fp                                       integral                               32    'hxxxxxxxx      
          file_open                                integral                               32    'h0             
          write_file_done                          integral                               32    'h0             
          write_section_done                       integral                               32    'h0             
          TRANSACTION_NUM                          integral                               32    'h0             
          transaction_num_idx                      integral                               32    'h0             
          TRANSACTION_DEPTH                        integral                               32    'h0             
          TRANSACTION_DEPTH_queue                  da(integral)                           0     -               
          TRANSACTION_DEPTH_queue_for_depth_check  da(integral)                           0     -               
          transaction_depth_idx                    integral                               32    'h0             
          ap_done_num_idx                          integral                               32    'h0             
        write_file_done_multi_out_multi_out        integral                               32    'h0             
        write_section_done_multi_out_multi_out     integral                               32    'h0             
      svr_master_multi_in0_imp                     uvm_analysis_imp_svr_master_multi_in0  -     @449            
      svr_master_multi_in1_imp                     uvm_analysis_imp_svr_master_multi_in1  -     @459            
      svr_slave_multi_out_imp                      uvm_analysis_imp_svr_slave_multi_out   -     @469            
    env_master_svr_multi_in0                       uvm_env                                -     @389            
    env_master_svr_multi_in1                       uvm_env                                -     @402            
    env_slave_svr_multi_out                        uvm_env                                -     @412            
    refm                                           multi_apuint_reference_model           -     @425            
    multi_apuint_virtual_sqr                       multi_apuint_virtual_sequencer         -     @479            
    multi_apuint_cfg                               multi_apuint_config                    -     @382            
      port_multi_in0_cfg                           svr_config                             -     @383            
        svr_type                                   svr_inst_type                          32    SVR_MASTER      
        prt_type                                   svr_protocol_type                      32    AP_HS           
        is_active                                  svr_active_passive_enum                1     SVR_ACTIVE      
        reset_level                                svr_reset_level_enum                   1     RESET_LEVEL_HIGH
        clatency                                   svr_latency_multi_in0                  -     @422            
          transfer_latency                         integral                               32    'h0             
      port_multi_in1_cfg                           svr_config                             -     @385            
        svr_type                                   svr_inst_type                          32    SVR_MASTER      
        prt_type                                   svr_protocol_type                      32    AP_HS           
        is_active                                  svr_active_passive_enum                1     SVR_ACTIVE      
        reset_level                                svr_reset_level_enum                   1     RESET_LEVEL_HIGH
        clatency                                   svr_latency_multi_in1                  -     @423            
          transfer_latency                         integral                               32    'h0             
      port_multi_out_cfg                           svr_config                             -     @387            
        svr_type                                   svr_inst_type                          32    SVR_SLAVE       
        prt_type                                   svr_protocol_type                      32    AP_HS           
        is_active                                  svr_active_passive_enum                1     SVR_ACTIVE      
        reset_level                                svr_reset_level_enum                   1     RESET_LEVEL_HIGH
        clatency                                   svr_latency_multi_out                  -     @424            
          transfer_latency                         integral                               32    'h0             
      check_ena                                    integral                               32    'h0             
      cover_ena                                    integral                               32    'h0             
----------------------------------------------------------------------------------------------------------------


UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(20867) @ 0: reporter [UVM/COMP/NAMECHECK] This implementation of the component name checks requires DPI to be enabled
UVM_INFO ./svtb/multi_apuint_subsys_test_sequence_lib.sv(17) @ 0: reporter@@multi_apuint_subsys_test_sequence_lib [multi_apuint_subsys_test_sequence_lib] new is called
UVM_INFO ./multi_apuint_subsystem/multi_apuint_env.sv(168) @ 0: uvm_test_top.top_env [uvm_test_top.top_env] multi_apuint_env is running
UVM_INFO ./file_agent/file_write_agent.sv(256) @ 0: reporter [file_wr_port_multi_out_multi_out] open file ../tv/rtldatafile/rtl.multi_apuint.autotvout_multi_out.dat for write
UVM_INFO ./file_agent/file_write_agent.sv(295) @ 0: reporter [file_wr_port_multi_out_multi_out] config write file with transaction number 10
UVM_INFO ./svr/svr_slave_monitor.sv(62) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon] run_phase is called
UVM_INFO ./svr/svr_slave_driver.sv(34) @ 0: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv [uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv] run_phase is called
UVM_INFO ./svr/svr_master_driver.sv(35) @ 0: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv] run_phase is called
UVM_INFO ./svr/svr_master_driver.sv(35) @ 0: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv [uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv] run_phase is called
UVM_INFO ./svtb/multi_apuint_subsys_test_sequence_lib.sv(45) @ 0: uvm_test_top.top_env.multi_apuint_virtual_sqr@@multi_apuint_subsys_test_sequence_lib [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib] get reference model by uvm_config_db
UVM_INFO ./svtb/multi_apuint_subsys_test_sequence_lib.sv(47) @ 0: uvm_test_top.top_env.multi_apuint_virtual_sqr@@multi_apuint_subsys_test_sequence_lib [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib] body is called
UVM_INFO ./svtb/multi_apuint_subsys_test_sequence_lib.sv(50) @ 0: uvm_test_top.top_env.multi_apuint_virtual_sqr@@multi_apuint_subsys_test_sequence_lib [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib] starting_phase not null
////////////////////////////////////////////////////////////////////////////////////
// Inter-Transaction Progress: Completed Transaction / Total Transaction
// Intra-Transaction Progress: Measured Latency / Latency Estimation * 100%
//
// RTL Simulation : "Inter-Transaction Progress" ["Intra-Transaction Progress"] @ "Simulation Time"
////////////////////////////////////////////////////////////////////////////////////
// RTL Simulation : 0 / 10 [0.00%] @ "125000"
UVM_INFO ./svr/svr_base_sequence.sv(45) @ 1145000: reporter@@svr_port_multi_in0_seq [svr_port_multi_in0_seq] new is called
UVM_INFO ./svr/svr_master_sequence.sv(21) @ 1145000: reporter@@svr_port_multi_in0_seq [svr_port_multi_in0_seq] new is called
UVM_INFO ./file_agent/file_read_agent.sv(142) @ 1145000: reporter [file_rd] open file ../tv/cdatafile/c.multi_apuint.autotvin_multi_in0.dat for read
UVM_INFO ./svr/svr_base_sequence.sv(45) @ 1145000: reporter@@svr_port_multi_in1_seq [svr_port_multi_in1_seq] new is called
UVM_INFO ./svr/svr_master_sequence.sv(21) @ 1145000: reporter@@svr_port_multi_in1_seq [svr_port_multi_in1_seq] new is called
UVM_INFO ./file_agent/file_read_agent.sv(142) @ 1145000: reporter [file_rd] open file ../tv/cdatafile/c.multi_apuint.autotvin_multi_in1.dat for read
UVM_INFO ./svr/svr_base_sequence.sv(45) @ 1145000: reporter@@svr_port_multi_out_seq [svr_port_multi_out_seq] new is called
UVM_INFO ./svr/svr_slave_sequence.sv(18) @ 1145000: reporter@@svr_port_multi_out_seq [svr_port_multi_out_seq] new is called
UVM_INFO ./svr/svr_master_sequence.sv(28) @ 1145000: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.sqr@@multi_apuint_subsys_test_sequence_lib.svr_port_multi_in0_seq [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in0_seq] body is called
UVM_INFO ./file_agent/file_read_agent.sv(344) @ 1145000: reporter [file_rd] read file done
UVM_INFO ./svr/svr_master_sequence.sv(28) @ 1145000: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.sqr@@multi_apuint_subsys_test_sequence_lib.svr_port_multi_in1_seq [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in1_seq] body is called
UVM_INFO ./file_agent/file_read_agent.sv(344) @ 1145000: reporter [file_rd] read file done
UVM_INFO ./svr/svr_slave_sequence.sv(23) @ 1145000: uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.sqr@@multi_apuint_subsys_test_sequence_lib.svr_port_multi_out_seq [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_out_seq] body is called
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1155000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1155000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1185000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1185000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1195000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1195000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1195000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1195000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
// RTL Simulation : 1 / 10 [50.00%] @ "1195000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1195000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1215000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1215000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1215000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1215000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 2 / 10 [100.00%] @ "1215000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1215000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1235000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1235000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1235000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1235000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
// RTL Simulation : 3 / 10 [150.00%] @ "1235000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1235000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1265000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1265000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1265000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1265000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
// RTL Simulation : 4 / 10 [200.00%] @ "1265000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1265000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1275000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1275000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1275000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1275000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
// RTL Simulation : 5 / 10 [150.00%] @ "1275000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1275000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1295000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1295000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1295000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1295000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 6 / 10 [100.00%] @ "1295000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1295000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1305000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1305000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1305000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1305000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 7 / 10 [100.00%] @ "1305000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1305000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(127) @ 1315000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_READY
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(80) @ 1315000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_ready_for_nexttrans
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1315000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1315000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 8 / 10 [50.00%] @ "1315000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1315000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./svr/svr_master_sequence.sv(90) @ 1315000: uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.sqr@@multi_apuint_subsys_test_sequence_lib.svr_port_multi_in0_seq [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in0_seq] send all TVs done
UVM_INFO ./svr/svr_master_sequence.sv(90) @ 1315000: uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.sqr@@multi_apuint_subsys_test_sequence_lib.svr_port_multi_in1_seq [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in1_seq] send all TVs done
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1325000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1325000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 9 / 10 [50.00%] @ "1325000"
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1325000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(119) @ 1355000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event DUT2TB_AP_DONE
UVM_INFO ./multi_apuint_subsystem/multi_apuint_reference_model.sv(102) @ 1355000: uvm_test_top.top_env.refm [uvm_test_top.top_env.refm] trigger event ap_done_for_nexttrans
// RTL Simulation : 10 / 10 [100.00%] @ "1355000"
////////////////////////////////////////////////////////////////////////////////////
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(54) @ 1355000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive ap_done_for_nexttrans and do axim dump
UVM_INFO ./svtb/multi_apuint_subsys_test_sequence_lib.sv(145) @ 1355000: uvm_test_top.top_env.multi_apuint_virtual_sqr@@multi_apuint_subsys_test_sequence_lib [uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib] autotb finished
UVM_INFO ./multi_apuint_subsystem/multi_apuint_scoreboard.sv(59) @ 1355000: uvm_test_top.top_env.subsys_mon.scbd [uvm_test_top.top_env.subsys_mon.scbd] receive FINISH
UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(19968) @ 1425000: reporter [TEST_DONE] 'run' phase is ready to proceed to the 'extract' phase
UVM_INFO /proj/xbuilds/SWIP/2020.1_0223_2001/installs/lin64/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv(13673) @ 1425000: reporter [UVM/REPORT/SERVER] [uvm_test_top.top_env.subsys_mon.scbd]    11
[uvm_test_top.top_env.refm]    40
[uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_out_seq]     1
[uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in1_seq]     2
[uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib.svr_port_multi_in0_seq]     2
[uvm_test_top.top_env.multi_apuint_virtual_sqr.multi_apuint_subsys_test_sequence_lib]     4
[uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.sqr]     1
[uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.mon]     3
[uvm_test_top.top_env.env_slave_svr_multi_out.s_agt.drv]     3
[uvm_test_top.top_env.env_slave_svr_multi_out]     1
[uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.sqr]     1
[uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.mon]     2
[uvm_test_top.top_env.env_master_svr_multi_in1.m_agt.drv]     3
[uvm_test_top.top_env.env_master_svr_multi_in1]     1
[uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.sqr]     1
[uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.mon]     2
[uvm_test_top.top_env.env_master_svr_multi_in0.m_agt.drv]     3
[uvm_test_top.top_env.env_master_svr_multi_in0]     1
[uvm_test_top.top_env]     4
[uvm_test_top]     1
[svr_port_multi_out_seq]     2
[svr_port_multi_in1_seq]     2
[svr_port_multi_in0_seq]     2
[multi_apuint_subsys_test_sequence_lib]     1
[file_wr_port_multi_out_multi_out]     2
[file_rd]     4
[UVMTOP]     1
[UVM/RELNOTES]     1
[UVM/COMP/NAMECHECK]     1
[TEST_DONE]     1
[RNTST]     1
[NO_DPI_TSTNAME]     1
** Report counts by id
UVM_FATAL :    0
UVM_ERROR :    0
UVM_WARNING :    0
UVM_INFO :  106
** Report counts by severity


--- UVM Report Summary ---


$finish called at time : 1425 ns : File "/media/masaaki/Ubuntu_Disk/tools/Xilinx/Vivado/2020.1/data/system_verilog/uvm_1.2/xlnx_uvm_package.sv" Line 18699
## quit
INFO: [Common 17-206] Exiting xsim at Thu Sep 10 03:40:42 2020...
INFO: [COSIM 212-316] Starting C post checking ...
multi_out = 0
multi_out = 2
multi_out = 6
multi_out = 12
multi_out = 20
multi_out = 30
multi_out = 42
multi_out = 56
multi_out = 72
multi_out = 90
INFO: [COSIM 212-1000] *** C/RTL co-simulation finished: PASS ***
Finished C/RTL cosimulation.


C/RTL 協調シミュレーションの全体波形を示す。
Vitis_HLS_vs_Vivado_HLS_53_200910.png

拡大波形を示す。
Vitis_HLS_vs_Vivado_HLS_54_200910.png

データ転送に Wait が入っているのが分かる。
この機能は良さそうだ。。。
  1. 2020年09月10日 04:18 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 その3 (C/RTL 協調シミュレーション、Export RTL)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 (C シミュレーション、C コードの合成)”の続き。

簡単な乗算回路で、Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は C シミュレーションと C コードの合成をやってみることにした。今回は、 C/RTL 協調シミュレーションと Export RTL をやっていこう。

Run C/RTL Cosimulation ボタンをクリックした。
Co-simulation ダイアログが開いた。

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_32_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_33_200907.png


Vitis HLS には、 Random Stall, Wave Debug (Vivado XSIM only), Channel (PIPO/FIFO) Profiling が追加されている。
Random Stall は”UG1399 (v2020.1) 2020 年 6 月 24 日 Vitis HLS ユーザーガイド”によると

各データ転送にランダムなストールを適用します。

ということだ。データ転送をランダムにストールさせて様子を見るのか? クロックが無いので、ストールはしないようだが、後で効果を見てみよう。
Wave Debug については”Vitis HLS 2020.1 の C/RTL 強調シミュレーション時の新機能1(Wave Debug)”を参照のこと。

C/RTL 協調シミュレーションの結果が表示された。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_36_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_37_200907.png


変化は無さそうだ。

C/RTL 協調シミュレーションの全体波形を表示した。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_38_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_39_200907.png


Vitis HLS の方がシミュレーション時間が長い。これはなぜだろうか?

C/RTL 協調シミュレーションの全体波形を拡大した。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_40_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_41_200907.png


こちらは違いはないようだ。

Export RTL ボタンをクリックした。
Export RTL ダイアログが開いた。
どちらも Vivado synthesis, place and route にチェックを入れた。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_42_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_43_200907.png



Export RTL の結果を確認する。
どちらも DSP 1個になってしまった。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_44_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_45_200907.png

  1. 2020年09月09日 04:43 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Vivado HLS 2020.1 vs Vitis HLS 2020.1 (C シミュレーション、C コードの合成)

Vivado HLS 2020.1 vs Vitis HLS 2020.1 (プロジェクトの作成)”の続き。

Vitis HLS 2020.1 と Vivado HLS 2020.1 を比較することにした。ということで、前回は、プロジェクトの作成までの違いを探っていたが、あまり違いは見られなかった。今回は、C シミュレーションと C コードの合成をやってみよう。

ソースコードとテストベンチコードを追加した。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_21_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_22_200907.png


C シミュレーションを行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_23_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_24_200907.png

C シミュレーションは同じのようだ。


C コードの合成を行う前に、Top Function を指定した。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_25_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_26_200907.png

Vitis HLS 2020.1 は余計というか、自分で作っていない関数がいっぱい表示されるのはなぜなのか?


C コードの合成を行った。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_27_200907.png

Vitis HLS 2020.1のデフォルトの表示はこれだが、Vivado HLS と同じ表示も syn の report を見ればある。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_28_200907.png
Vitis_HLS_vs_Vivado_HLS_29_200907.png


合成後の Verilog HDL ファイルを比較する。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_34_200907.png

トップの multi_apuint.v と multi_apuint_mul_8ns_8ns_16_1_1.v の 2 つの Verilog HDL ファイルができている。

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_35_200907.png

トップの multi_apuint.v の 1 つだけだ。


Verilog HDL のコードを貼っておく。

Vitis HLS 2020.1 の multi_apuint.v を示す。

// ==============================================================
// RTL generated by Vitis HLS - High-Level Synthesis from C, C++ and OpenCL
// Version: 2020.1
// Copyright (C) 1986-2020 Xilinx, Inc. All Rights Reserved.
// 
// ===========================================================

`timescale 1 ns / 1 ps 

(* CORE_GENERATION_INFO="multi_apuint_multi_apuint,hls_ip_2020_1,{HLS_INPUT_TYPE=cxx,HLS_INPUT_FLOAT=0,HLS_INPUT_FIXED=0,HLS_INPUT_PART=xc7z020-clg400-1,HLS_INPUT_CLOCK=10.000000,HLS_INPUT_ARCH=others,HLS_SYN_CLOCK=4.170000,HLS_SYN_LAT=0,HLS_SYN_TPT=none,HLS_SYN_MEM=0,HLS_SYN_DSP=0,HLS_SYN_FF=0,HLS_SYN_LUT=41,HLS_VERSION=2020_1}" *)

module multi_apuint (
        ap_start,
        ap_done,
        ap_idle,
        ap_ready,
        multi_in0,
        multi_in1,
        multi_out,
        multi_out_ap_vld
);


input   ap_start;
output   ap_done;
output   ap_idle;
output   ap_ready;
input  [7:0] multi_in0;
input  [7:0] multi_in1;
output  [15:0] multi_out;
output   multi_out_ap_vld;

reg multi_out_ap_vld;

wire   [15:0] mul_ln1349_fu_51_p2;
wire   [7:0] mul_ln1349_fu_51_p0;
wire   [7:0] mul_ln1349_fu_51_p1;
wire   [15:0] mul_ln1349_fu_51_p00;
wire   [15:0] mul_ln1349_fu_51_p10;

multi_apuint_mul_8ns_8ns_16_1_1 #(
    .ID( 1 ),
    .NUM_STAGE( 1 ),
    .din0_WIDTH( 8 ),
    .din1_WIDTH( 8 ),
    .dout_WIDTH( 16 ))
mul_8ns_8ns_16_1_1_U1(
    .din0(mul_ln1349_fu_51_p0),
    .din1(mul_ln1349_fu_51_p1),
    .dout(mul_ln1349_fu_51_p2)
);

always @ (*) begin
    if ((ap_start == 1'b1)) begin
        multi_out_ap_vld = 1'b1;
    end else begin
        multi_out_ap_vld = 1'b0;
    end
end

assign ap_done = ap_start;

assign ap_idle = 1'b1;

assign ap_ready = ap_start;

assign mul_ln1349_fu_51_p0 = mul_ln1349_fu_51_p00;

assign mul_ln1349_fu_51_p00 = multi_in1;

assign mul_ln1349_fu_51_p1 = mul_ln1349_fu_51_p10;

assign mul_ln1349_fu_51_p10 = multi_in0;

assign multi_out = mul_ln1349_fu_51_p2;

endmodule //multi_apuint


Vitis HLS 2020.1 の multi_apuint_mul_8ns_8ns_16_1_1.v を示す。

// ==============================================================
// Vitis HLS - High-Level Synthesis from C, C++ and OpenCL v2020.1 (64-bit)
// Copyright 1986-2020 Xilinx, Inc. All Rights Reserved.
// ==============================================================

`timescale 1 ns / 1 ps

module multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0(a, b, p);
input[8 - 1 : 0] a; 
input[8 - 1 : 0] b; 
output[16 - 1 : 0] p;

assign p = $signed({1'b0, a}) * $signed({1'b0, b});
endmodule
`timescale 1 ns / 1 ps
module multi_apuint_mul_8ns_8ns_16_1_1(
    din0,
    din1,
    dout);

parameter ID = 32'd1;
parameter NUM_STAGE = 32'd1;
parameter din0_WIDTH = 32'd1;
parameter din1_WIDTH = 32'd1;
parameter dout_WIDTH = 32'd1;
input[din0_WIDTH - 1:0] din0;
input[din1_WIDTH - 1:0] din1;
output[dout_WIDTH - 1:0] dout;



multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0 multi_apuint_mul_8ns_8ns_16_1_1_Multiplier_0_U(
    .a( din0 ),
    .b( din1 ),
    .p( dout ));

endmodule



Vivado HLS 2020.1 の multi_apuint.v を示す。

// ==============================================================
// RTL generated by Vivado(TM) HLS - High-Level Synthesis from C, C++ and OpenCL
// Version: 2020.1_AR75369
// Copyright (C) 1986-2020 Xilinx, Inc. All Rights Reserved.
// 
// ===========================================================

`timescale 1 ns / 1 ps 

(* CORE_GENERATION_INFO="multi_apuint,hls_ip_2020_1_AR75369,{HLS_INPUT_TYPE=cxx,HLS_INPUT_FLOAT=0,HLS_INPUT_FIXED=1,HLS_INPUT_PART=xc7z020-clg400-1,HLS_INPUT_CLOCK=10.000000,HLS_INPUT_ARCH=others,HLS_SYN_CLOCK=4.170000,HLS_SYN_LAT=0,HLS_SYN_TPT=none,HLS_SYN_MEM=0,HLS_SYN_DSP=0,HLS_SYN_FF=0,HLS_SYN_LUT=41,HLS_VERSION=2020_1_AR75369}" *)

module multi_apuint (
        ap_start,
        ap_done,
        ap_idle,
        ap_ready,
        multi_in0_V,
        multi_in1_V,
        multi_out_V,
        multi_out_V_ap_vld
);


input   ap_start;
output   ap_done;
output   ap_idle;
output   ap_ready;
input  [7:0] multi_in0_V;
input  [7:0] multi_in1_V;
output  [15:0] multi_out_V;
output   multi_out_V_ap_vld;

reg multi_out_V_ap_vld;

wire   [7:0] ret_V_fu_43_p0;
wire   [7:0] ret_V_fu_43_p1;
wire   [15:0] ret_V_fu_43_p00;
wire   [15:0] ret_V_fu_43_p10;

always @ (*) begin
    if ((ap_start == 1'b1)) begin
        multi_out_V_ap_vld = 1'b1;
    end else begin
        multi_out_V_ap_vld = 1'b0;
    end
end

assign ap_done = ap_start;

assign ap_idle = 1'b1;

assign ap_ready = ap_start;

assign multi_out_V = (ret_V_fu_43_p0 * ret_V_fu_43_p1);

assign ret_V_fu_43_p0 = ret_V_fu_43_p00;

assign ret_V_fu_43_p00 = multi_in1_V;

assign ret_V_fu_43_p1 = ret_V_fu_43_p10;

assign ret_V_fu_43_p10 = multi_in0_V;

endmodule //multi_apuint


Analysis 画面を貼っておく。

Vitis HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_30_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_31_200907.png

これは、違わない。

  1. 2020年09月08日 04:07 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

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 から Vitis HLS への移行は”Vitis HLS 移行ガイド UG1391 (v2020.1) 2020 年 7 月 28 日”を参照のこと。

使用するプロジェクトは大学の最初の課題の multi_apuint にする。掛け算だけのとっても簡単なプロジェクトだ。
ソースコードの multi_apuint.cpp を示す。

// multi_apuint.cpp

#include <ap_int.h>

void multi_apuint(ap_uint<8> multi_in0, ap_uint<8> multi_in1,
        ap_uint<16> *multi_out){
    *multi_out = multi_in0 * multi_in1;
}


テストベンチ・コードの muti_apuint_tb.cpp を示す。

#include <string.h>
#include <ap_int.h>

void multi_apuint(ap_uint<8> multi_in0, ap_uint<8> multi_in1,
        ap_uint<16> *multi_out);

int main(){
    using namespace std;

    ap_uint<8> multi_in0;
    ap_uint<8> multi_in1;
    ap_uint<16> multi_out;

    for (multi_in0=0, multi_in1=1; multi_in0<10; multi_in0++, multi_in1++){
        multi_apuint(multi_in0, multi_in1, &multi_out);
        cout << "multi_out = " << multi_out << endl;
        if (multi_out != (multi_in0 * multi_in1))
            return(1);
    }

    return(0);
}


次から、Vitis HLS 2020.1 と Vivado HLS 2020.1 を交互にブログに貼っていって、同じ動作のGUI 表示を括っていく。

まずは、Vitis HLS 2020.1 から起動した。
Vitis_HLS_vs_Vivado_HLS_9_200907.png

Create Project をクリックする。

Vivado HLS 2020.1 を起動した。
Vitis_HLS_vs_Vivado_HLS_10_200907.png

Create New Project をクリックする。


Project Configuration

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_11_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_12_200907.png


Add/Remove Files
Add/remove C-based source files (design specification)

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_13_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_14_200907.png


Add/Remove Files
Add/remove C-based testbench files (design test)

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_15_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_16_200907.png


Solution Configuration

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_17_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_18_200907.png


multi_apuint プロジェクト起動画面

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_19_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_20_200907.png


multi_apuint プロジェクトに multi_apuint.cpp と mult_apuint_tb.cpp を登録した。

Viits HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_21_200907.png

Vivado HLS 2020.1
Vitis_HLS_vs_Vivado_HLS_22_200907.png


最初の起動 GUI は違っていたが、プロジェクトを作成するダイアログは Solution Configuration 以外は違いがない。
  1. 2020年09月07日 05:05 |
  2. Vitis HLS
  3. | トラックバック:0
  4. | コメント:0

Zynq のベアメタル・アプリケーションによるキャッシュの操作3(Vitis でのキャッシュ操作について)

Zynq のベアメタル・アプリケーションによるキャッシュの操作2(ACPポート)”の続き。

前回までは、Vivado HLS 2019.2 で AXI4 Master インターフェースを持つ 2乗 IP を作成して、Vivado 2019.2 で 2乗 IP を Add IP して回路を作成した。AXI_ACP ポートを使用して、キャッシュに書けるようにし、キャッシュ・フラッシュ関数(Xil_DCacheFlush())を呼ばなくても正常に表示できるかを確かめてみたところ、結果を収納する配列を初期化していると、うまく行かなかった。今回は、Zynq のキャッシュの振る舞いについて、更に調べてみよう。

AXI_ACP ポートを使用して、キャッシュに書けるようにた回路で、結果を収納する配列を初期化するのが、Vivado HLS で作成した 2 乗 IP が結果を格納するより、後になってしまっているのでは?という疑惑を確かめるために、C ソースコードに同期を入れてみることにした。

少なくとも SDK でのインライン・アセンブラの書き方は”AR# 61480 SDK、GCC - GCC ツールチェーンでの VCVTR 命令の使用方法”にあるようだ。そのインライン・アセンブラを引用する。

__asm__ __volatile__("VCVTR.S32.F32 s15, s15;");


Cortex-A9 の同期命令は”Zynq-7000 SoC テクニカル リファレンス マニュアル UG585 (v1.10) 2015 年 2 月 23 日”の 68 ~ 70 ページによると、次の 3 つがある。

データ メモリ バリア (DMB)
デー タ同期バ リ ア (DSB)
命令同期バ リ ア (ISB)


がある。
これを C コードに埋め込んだ。

__asm__ __volatile__("DSB");
__asm__ __volatile__("ISB");

XDma_pow2_Set_in_r(&XDMA_pow2_ap, (u32)&data[0]);


zynq_cache_23_200905.png

コンパイルは通るのだが、text エリアが増えない。これはなぜだろう?
実行結果は正常ではなかった。
zynq_cache_20_200904.png

AXI_ACP ポートを使用していても、Xil_DCacheFlush(); を入れると結果が正常になる。
zynq_cache_24_200905.png

zynq_cache_21_200904.png

う~~~ん。謎だ。


AXI_HP ポートで接続した実装でも、data[10] 配列を初期化してから Xil_DCacheFlush() して、2 乗の DMA してから、Xil_DCacheInvalidate() するのが本当じゃないか?と思ったので、やってみた。

/* * test_dma.c * *  Created on: 2017/12/02 *      Author: masaaki */

#include <stdio.h>
#include "xdma_pow2.h"
#include "xparameters.h"

volatile int data[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
//volatile int result[10];
volatile int result[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};

void Xil_DCacheFlush(void);
void Xil_DCacheInvalidate(void);

int main(){
    XDma_pow2 XDMA_pow2_ap;
    XDma_pow2_Config *XDMA_pow2_apPtr;
    int i;

    printf("%x\n", (unsigned int)data);
    printf("%x\n", (unsigned int)result);

    // Look Up the device configuration
    XDMA_pow2_apPtr = XDma_pow2_LookupConfig(0);
    if (!XDMA_pow2_apPtr){
        fprintf(stderr, "XDma_pow2 configuration failed.\n");
        return(-1);
    }

    // Initialize the Device
    int Xlap_status = XDma_pow2_CfgInitialize(&XDMA_pow2_ap, XDMA_pow2_apPtr);
    if (Xlap_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XDma_pow2\n");
        return(-1);
    }

    XDma_pow2_Set_in_r(&XDMA_pow2_ap, (u32)&data[0]);
    XDma_pow2_Set_out_r(&XDMA_pow2_ap, (u32)&result[0]);

    Xil_DCacheFlush();

    XDma_pow2_Start(&XDMA_pow2_ap);

    while(!XDma_pow2_IsDone(&XDMA_pow2_ap)) ;

    Xil_DCacheInvalidate();

    for(i=0; i<10; i++){
        printf("data[%d] = %d, result[%d] = %d\n", i, data[i], i, result[i]);
    }

    return 0;

}


これで結果は正常だが、そもそも Xil_DCacheInvalidate(); が無くても正常動作だ。

Vitis でのベアメタル・アプリケーションでのキャッシュを操作する関数は、”xil_cache_l.h”を参照すれば良いのだと思う。

(追記)
Xil_DCacheFlush(); でキャッシュはインバリデートされるということだったので、後の Xil_DCacheInvalidate(); は要らないことが分かりました。これは実際の動作とも合致しています。 tom01h さん、教えていただいて、ありがとうございました。

(2020/09/07:追記)
tom01h さんのブログを参照として追加しておきます。
tiny-dnn アクセラレータをパイプライン動作させる データバッファ編 その4
  1. 2020年09月05日 06:12 |
  2. Zynq
  3. | トラックバック:0
  4. | コメント:0

Zynq のベアメタル・アプリケーションによるキャッシュの操作2(ACPポート)

Zynq のベアメタル・アプリケーションによるキャッシュの操作2(Xil_DCacheFlush())”の続き。

(2021/04/30:追記) この問題に関する回答は”Zynq のベアメタル・アプリケーションによるキャッシュの操作3(ACPポート2)”をご覧ください。

前回は、 Vivado HLS 2019.2 で AXI4 Master インターフェースを持つ 2乗 IP を作成して、Vivado 2019.2 で 2乗 IP を Add IP して回路を作成する。その回路のビットストリームを作成し、XSA ファイルを出力してから Vitis 2019.2 を起動して、プラットフォームとアプリケーション・プロジェクトを作成する。アプリケーション・プロジェクトで作成された elf ファイルを実行してみよう。キャッシュの操作が無いとデータがおかしくなるが、Xil_DCacheFlush() を入れると正常になった。今回は同様の回路を使用するが、AXI_ACP ポートを使用して、キャッシュに書けるようにし、キャッシュ・フラッシュ関数(Xil_DCacheFlush())を呼ばなくても正常に表示できるかを確かめてみよう。

前回のDMA_pow2_test プロジェクトのフォルダをコピーして、DMA_pow2_test2 と名前を変えた。
zynq_cache_14_200903.png

前回と回路は同様だが、ZYNQ7 Processing System の AXI_ACP ポートに DMA_pow2 を接続した。ブロックデザインを示す。
zynq_cache_15_200903.png

DMA_pow2 の設定は、Enable USER ports のチェックを入れて、USER value を 1 に、CACHE value を "1111" に指定した。これで、キャッシュに書けるはずだ。
zynq_cache_16_200903.png

Address Editor を示す。
zynq_cache_17_200903.png

論理合成、インプリメンテーション、ビットストリームの生成を行った。結果を示す。
zynq_cache_18_200903.png

ハードウェアをエクスポートして、Vitis を立ち上げて、プラットフォームとアプリケーション・プロジェクトを作成し、アプリケーション・プロジェクトに前回と同じ test_dma.c をインポートした。
zynq_cache_19_200903.png

前回と同様の test_dma.c で Xil_DCacheFlush() をコメントアウトして、FPGAをコンフィグレーションし、ソフトウェアを起動した。
zynq_cache_20_200904.png

なんと、前回の AXI_HP ポートと同様に値がおかしい。。。
AXI_ACP ポートに接続したのに。。。原因を考えてみると、test_dma.c を見ると分かるが、ハードウェアの入力の data[10] も出力の result[10] も値を初期化している。キャッシュON だと通常はキャッシュに書かれるので、ここで当該キャッシュ・ラインをフラッシュする必要があるのだと思う。コードが足りないわけだ。
そして、このソフトウェアでは、キャッシュをフラッシュしなくても、メモリに書かれているようだ。ということで、今回の原因としては、DMA で 2 乗した結果をキャッシュに書かれた後で CPU の Write Buffer に残っていた result[7], result[8], result[9] に書いてしまったということはないだろうか? (大胆な推測。。。)

ちなみに、test_dma.c の配列の定義を変えて result[10] のデータを初期化しないと(当然 Xil_DCacheFlush() 関数は入れていない)

volatile int data[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
volatile int result[10];
//volatile int result[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};


正常な値になる。
zynq_cache_21_200904.png

前回の AXI_HP ポートに接続された回路で同様に result[10] のデータを初期化しないで、Xil_DCacheFlush() 関数も入れないと結果はすべて 0 になった。
zynq_cache_22_200904.png

この状態で、 Xil_DCacheFlush() 関数をいれると正常に 2 乗されている。

AXI_ACP ポートでキャッシュに書く効果は表れているが、よくよく気を付けないとキャッシュに書けると油断していると危ないようだ。
いろいろとご意見を募集します。コメント欄やツィッターで教えてください。

以前、PowerPC を使っているときに、シリアルだったと思うが、制御用 IC のコマンドレジスタに Write してからステータスレジスタを Read して分岐していたが、どうもプログラムが正常に動作しないことがあった。詳しくトレースしてみると、コマンドレジスタに Write する前に、ステータスレジスタを Read して分岐されてしまっていた。アウト・オブ・オーダーの弊害?のようだった。これには相当ショックを受けた。 C で書いていたのにアセンブラで解析することになってしまったし。。。
そこで、PowerPC ではeieio (I/O 順次実行強制命令)があったので、C にアセンブラコードを埋め込んで、IO の順序を強制した。
それからはコードには十分注意して、eieio や sync, isync を C コードに埋め込む日々になってしまった。orz
(ちなみに、優秀な学生さんと一緒に解析しました。彼がいないと解析できなかったです。私はハード担当なので。。。C コードに埋め込んだのも学生さんです。私はそれを検証したと思います。デバック一緒にやっていたので。。。)

CPUって本当にレイジーなコンシステンシー・システム持っているので、うかうかコード書いていると、とっても危ない。。。
  1. 2020年09月04日 05:23 |
  2. Zynq
  3. | トラックバック:0
  4. | コメント:0

Zynq のベアメタル・アプリケーションによるキャッシュの操作2(Xil_DCacheFlush())

Zynq のベアメタル・アプリケーションによるキャッシュの操作1(説明編)”の続き。

前回は、Zynq ( Cortex-A9 プロセッサと FPGA が搭載されているチップ)のキャッシュにかかわる動作について、キャッシュによる不具合をスライドで説明した。今回は、実際に Vivado HLS 2019.2 で AXI4 Master インターフェースを持つ 2乗 IP を作成して、Vivado 2019.2 で 2乗 IP を Add IP して回路を作成する。その回路のビットストリームを作成し、XSA ファイルを出力してから Vitis 2019.2 を起動して、プラットフォームとアプリケーション・プロジェクトを作成する。アプリケーション・プロジェクトで作成された elf ファイルを実行してみよう。キャッシュの操作が無いとデータがおかしくなるが、Xil_DCacheFlush() を入れると正常になる。

Vivado HLS 2019.2 で作った DMA_pow2 プロジェクトを紹介する。
zynq_cache_4_200903.png

DMA_pow2.cpp は AXI4 Master インターフェースの 2 乗 IP だ。 in のアドレスの配列から 10 個取ってきて、2 乗して out の配列に結果を書く。

C コードの合成結果を示す。
zynq_cache_5_200903.png

Export RTL の結果を示す。
zynq_cache_6_200903.png

Vivado 2019.2 の DMA_pow2_test プロジェクトを作成した。
zynq_cache_7_200903.png

DMA_pow2 IP を使用したブロックデザインを示す。
DMA_pow2 IP は Zynq プロセッサの HP ポートに接続されているので、キャッシュではなく DDR SDRAM から Read/Write するようになる。
zynq_cache_8_200903.png

論理合成、インプリメンテーション、ビットストリームの生成を行った。Project Summary を示す。
zynq_cache_9_200903.png

ハードウェアをエクスポート( XSA ファイルを出力)して、Vitis 2019.2 を起動して、ワークスペースを指定した。
プラットフォームとアプリケーション・プロジェクトを作成した。
最初に Xil_DCacheFlush() 関数をコメントアウトしておく。
zynq_cache_10_200903.png

test_dma.elf を実行させると 7 番目からが 2 乗されていない。
zynq_cache_11_200903.png

Xil_DCacheFlush() 関数のコメントアウトを外してコンパイルして Run した。
zynq_cache_12_200903.png

test_dma.elf を実行させると正常動作した。
zynq_cache_13_200903.png

このようにキャッシュを適切に扱う必要がある。

Xil_DCacheFlush() 関数の他に指定されたキャッシュラインをフラッシュする Xil_DCacheFlushLine() 関数もある。
参照ブログ
ZedBoardにビットマップ・ディスプレイ・コントローラを追加する16(ARMのソフトからキャラクタを書けた)
ZedBoardにビットマップ・ディスプレイ・コントローラを追加する17(ARMのソフトからキャラクタを書けた2)

test_dma.c を貼っておく。

/* * test_dma.c * *  Created on: 2017/12/02 *      Author: masaaki */

#include <stdio.h>
#include "xdma_pow2.h"
#include "xparameters.h"

volatile int data[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
volatile int result[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};

void Xil_DCacheFlush(void);

int main(){
    XDma_pow2 XDMA_pow2_ap;
    XDma_pow2_Config *XDMA_pow2_apPtr;
    int i;

    // Look Up the device configuration
    XDMA_pow2_apPtr = XDma_pow2_LookupConfig(0);
    if (!XDMA_pow2_apPtr){
        fprintf(stderr, "XDma_pow2 configuration failed.\n");
        return(-1);
    }

    // Initialize the Device
    int Xlap_status = XDma_pow2_CfgInitialize(&XDMA_pow2_ap, XDMA_pow2_apPtr);
    if (Xlap_status != XST_SUCCESS){
        fprintf(stderr, "Could not Initialize XDma_pow2\n");
        return(-1);
    }

    XDma_pow2_Set_in_r(&XDMA_pow2_ap, (u32)&data[0]);
    XDma_pow2_Set_out_r(&XDMA_pow2_ap, (u32)&result[0]);

    Xil_DCacheFlush();

    XDma_pow2_Start(&XDMA_pow2_ap);

    while(!XDma_pow2_IsDone(&XDMA_pow2_ap)) ;

    for(i=0; i<10; i++){
        printf("data[%d] = %d, result[%d] = %d\n", i, data[i], i, result[i]);
    }

    return 0;

}

  1. 2020年09月03日 06:38 |
  2. Zynq
  3. | トラックバック:0
  4. | コメント:0

Zynq のベアメタル・アプリケーションによるキャッシュの操作1(説明編)

今日から筑波大学で 2020 年度の Vivado HLS セミナを始めるが、その教材の一部をご紹介する。
それは、Zynq ( Cortex-A9 プロセッサと FPGA が搭載されているチップ)のキャッシュにかかわる動作についてだ。

今日はその説明で、キャッシュによる不具合をスライドで説明する。

赤い四角が CPU コアでキャッシュと分離されている。 1 次、2 次キャッシュを含めたキャッシュのモデルが Cache となる。その右にメモリのモデルが Memory として書いてある。Cache と Memory は箱の集まりになっているが、これの 1 つの箱が 1 つのキャッシュ・ラインを示す。DMAC はDMA コントローラを示している。
今最初の図で、キャッシュされたキャッシュ・ラインは黄色で示されている。2 番目と 4 番目のキャッシュ・ラインがキャッシュに入っている。
この状態で 2 番目の図のように、その Memory に Zynq の HP ポート(メモリに書くためのポート)に接続された DMAC でメモリにデータを書くとどうなるだろう。CPU はメモリに DMAC がデータを書き換えたことをまだ知らないが、メモリは書き換えらえて、2 番目と 4 番目のキャッシュ・ラインがキャッシュに入ったままだ。
zynq_cache_1_200902.png

CPU が 1 番目から 4 番目の番地のメモリからデータを読もうとすると、1 番目と 3 番目のデータは DMAC で書かれた必要とするデータが読み込まれるが、2 番目と 4 番目のキャッシュ・ラインは有効なので、そこは、古いキャッシュのデータが読み込まれる。(3 番目の図)
これでは、まずいので、どうやるかというと DMA する場合に、DMA するメモリ領域をキャッシュしているキャッシュ・ラインをすべてフラッシュして、キャッシュをメモリに書き戻してから(書き換えるので、無効でもよいと思うが)、DMAC でメモリに書く必要がある。 2 番目の図では、当該キャッシュ・ラインを無効にしている。これは、CPU のソフトウェアで命令を発行して、明示的にキャッシュをフラッシュまたは無効にする。
zynq_cache_2_200902.png

その後、DMAC でデータを DMA して CPU が読めば、DMA されたデータが正しく読める。(1 番目の図)

また、2 番目の図では ACP ポートを経由してキャッシュに直接書く場合の図となっている。この場合は、明示的に CPU のソフトウェアで命令を発行する必要はない。
zynq_cache_3_200902.png

キャッシュに書く場合に DMA の量が大きくて、キャッシュに全部書けない場合は、古いデータをメモリに書き出して、あふれたデータをそのキャッシュに書きこむ動作を続けることになる(LRU の場合)。

キャッシュの動作については、ウィキペディアの”MESIプロトコル”や”ヘネシー&パターソン コンピュータアーキテクチャ 定量的アプローチ 第5版のMESIプロトコル”、”MESIプロトコルとMOESIプロトコル”を参照のこと。(いしたにさん、有用なサイトを教えていただいてありがとうございました)

さて、これらを実機で体験しよう。
  1. 2020年09月02日 05:29 |
  2. Zynq
  3. | トラックバック:0
  4. | コメント:0