前回
ドキュメントを読んだ.
前回の記事:Alveo U250でXPM_MEMORY_SPRAMを使いたい(1)
githubのソースを使ってみる
githubでXPM_MEMORY_SPRAMを使っているモジュールを見つけたので,使ってみる.
Github:pulp-platform/tech_cells_generic
(https://github.com/pulp-platform/tech_cells_generic)
githubの該当のソースコードを書き換え
tech_cells_generic/src/fpga/tc_sram_xilinx.sv
を使ってみようと思う.
ただこのままでは初期化用のファイルを指定できない.
設定できるようにしよう.
parameterInitFile
で初期化ファイルを指定するようにする
次のように書き換える.
32
33
34
|
parameter type data_t = logic [DataWidth-1:0],
parameter type be_t = logic [BeWidth-1:0],
parameter InitFile = "none" // 追加:初期化ファイル
|
各モジュールのMEMORY_INIT_FILE
にInitFile
を割り当て
Single Port RAMのモジュール
まずはxpm_memory_spram: Single Port RAM
側を2箇所80,81行目
を編集.
73
74
75
76
77
78
79
80
81
82
|
// xpm_memory_spram: Single Port RAM
// XilinxParameterizedMacro, version 2018.1
xpm_memory_spram#(
.ADDR_WIDTH_A ( AddrWidth ), // DECIMAL
.AUTO_SLEEP_TIME ( 0 ), // DECIMAL
.BYTE_WRITE_WIDTH_A ( ByteWidth ), // DECIMAL
.ECC_MODE ( "no_ecc" ), // String
.MEMORY_INIT_FILE ( InitFile ), // 書き換え:String
.MEMORY_INIT_PARAM ( "" ), // 書き換え:String
.MEMORY_OPTIMIZATION ( "true" ), // String
|
True Dual Port RAMのモジュール
次にxpm_memory_tdpram: True Dual Port RAM
側を2箇所119,120行目
を編集.
109
110
111
112
113
114
115
116
117
118
119
120
121
|
// xpm_memory_tdpram: True Dual Port RAM
// XilinxParameterizedMacro, version 2018.1
xpm_memory_tdpram#(
.ADDR_WIDTH_A ( AddrWidth ), // DECIMAL
.ADDR_WIDTH_B ( AddrWidth ), // DECIMAL
.AUTO_SLEEP_TIME ( 0 ), // DECIMAL
.BYTE_WRITE_WIDTH_A ( ByteWidth ), // DECIMAL
.BYTE_WRITE_WIDTH_B ( ByteWidth ), // DECIMAL
.CLOCKING_MODE ( "common_clock" ), // String
.ECC_MODE ( "no_ecc" ), // String
.MEMORY_INIT_FILE ( InitFile ), // 書き換え:String
.MEMORY_INIT_PARAM ( "" ), // 書き換え:String
.MEMORY_OPTIMIZATION ( "true" ), // String
|
これでよし.
テストベンチファイル作成
テストベンチを作る.
まあ細かい動作確認はするつもりなくて,アドレスから正しい値を読めるかなあって確認だけ.
それってテストベンチか?
とりあえず./test/tb_tc_sram_origin.sv
を作成.
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
|
`timescale 1ns / 1ps
// ----- 定数たち -----
`define DATA_WIDTH 128
`define ADDR_WIDTH 10
// --------------------
module tb_tc_sram_origin;
// ----- クロックの動作 -----
logic clk_i;
initial begin
clk_i <= 1'b0;
#2;
forever begin
#1; clk_i <= (clk_i==1'b1)?1'b0:1'b1;
end
end
// --------------------
// ----- メモリの動作 -----
// // モジュールの宣言
logic rst_ni;
logic req_i;
logic we_i;
logic [ `ADDR_WIDTH -1:0] addr_i;
logic [ `DATA_WIDTH -1:0] wdata_i;
logic [ (`DATA_WIDTH/8) -1:0] be_i;
logic [ `DATA_WIDTH -1:0] rdata_o;
// // モジュールの宣言
tc_sram #(
.NumWords ( 2**(`ADDR_WIDTH) ),
.NumPorts ( 1 ),
.DataWidth ( `DATA_WIDTH ),
.SimInit ( "random" ),
.InitFile ( "hello_world.mem" )
) ram_0 (
.clk_i ( clk_i ),
.rst_ni ( rst_ni ),
.req_i ( req_i ),
.we_i ( we_i ),
.addr_i ( 10'h0 + addr_i[($clog2(2**10)+$clog2(`DATA_WIDTH/8)) -1:$clog2(`DATA_WIDTH/8)] ),
.wdata_i( wdata_i ),
.be_i ( be_i ),
.rdata_o( rdata_o )
);
// // 各信号の制御
initial begin
$dumpfile( "result.vcd" );
$dumpvars( 0, ram_0 );
#10; //全信号の初期化
rst_ni <= 1'b1;
req_i <= 1'b0;
we_i <= 1'b0;
addr_i <= 10'h000;
wdata_i <= 128'h00000000000000000000000000000000;
be_i <= 16'hFFFF;
#10; // リセット:ON
rst_ni <= 1'b0;
#10; // リセット:OFF
rst_ni <= 1'b1;
#10; // 0x0000から値を読み取り
addr_i <= 10'h000;
req_i <= 1'b1;
#10; // req_iを下げる
req_i <= 1'b0;
#10; // 0x0010から値を読み取り
addr_i <= 10'h010;
req_i <= 1'b1;
#10; // req_iを下げる
req_i <= 1'b0;
#10; // おしまい
$finish;
end
endmodule
|
テストベンチの実行
当然だけど,iverilog
コマンドでは動作確認できない...まあVivado
でやりましょう.
次のtclファイルをtcl/test.tcl
って名前で作りましょ.
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
# -----変数-------------
set outputDir "./output" ; # プロジェクトのディレクトリを設定
set projectName "vivado_prj" ; # プロジェクト名を設定
set device_name "xilinx.com:au250:part0:1.3" ; # デバイス名を設定
set part_name "xcu250-figd2104-2L-e" ; # fpgaチップ名を設定
# -----前回の実行結果を削除-------------
file delete -force $outputDir
file mkdir $outputDir
# -----プロジェクトの作成-------------
create_project -force $projectName $outputDir -part $part_name ;# プロジェクトファイル作成
set_property board_part $device_name [current_project] ;# FPGA
update_ip_catalog ;
# -----シミュレーション時間の制限を削除-------------
set_property -name {xsim.simulate.runtime} -value {-all} -objects [get_filesets sim_1]
# -----ソースを追加-------------
add_file test/tb_tc_sram_origin.sv
add_file src/fpga/tc_sram_xilinx.sv
add_file test/hello_world.mem
# -----トップモジュールを設定-------------
set_property top tb_tc_sram_origin [current_fileset]
set_property top tb_tc_sram_origin [get_filesets sim_1]
# -----シミュレーション実行-------------
update_compile_order -fileset sources_1
launch_simulation
source $outputDir/$projectName.sim/sim_1/behav/xsim/tb_tc_sram_origin.tcl
# ----プロジェクトを閉じる-------------
close_project
|
そのあと以下のコマンドを実行する.
0
|
vivado -mode batch -source test/test.tcl
|
最後に以下のコマンドを実行して作成したvcdファイルを確認.
0
|
gtkwave ./output/vivado_prj.sim/sim_1/behav/xsim/result.vcd
|
実行結果はこんな感じ

読めてそう.色々使えることがあるところがあると嬉しいな.