EDITORIAL言葉
多くの場合、我々は、格納された取得するデータを収集する必要があり、再呼び出しをする時間が必要になるまで。これが事実であるならば、私たちのメモリは読み書き可能でなければなりませんお願いします。このセクションでは、翼の兄弟の夢と一緒に勉強 FPGA 書き込み可能なメモリのIP コア-RAM 使用します。
プロジェクト要件
設計のRAM を担当するコントローラRAM の読み書き操作、データが最初に書き込まれるRAM 、その後、すべてのデータを読み取ります。データが書き込まれると、まったく同じ読みされている場合は、私たちは、操作やデザインを修正していること。
ステップ
右側でのIP コアの検索フィールド、型RAM 、見つけて、メニューバーをダブルクリックし、[ RAM : 1-PORT ]
言語の種類を選択したVerilog 、および名前をクリックし、[ OK ]
設定されたRAM メモリ深さと、各収納スペースのビット数を、[OK]をクリックし、[ NEXT ]
[Q出力ポート] キャンセルするフックの前に(キャンセルされない場合は、出力が遅ればせながらされ、出力ポートレジスタで生成されますが、ここではそれが遅ればせながら必要はありません)、[OK]をクリックします [NEXT]
[クリックして続行 NEXTを次の画面まで]を選択しmy_ram_inst.v 、[]をクリックし[完了]完了するために、ラムの設定を
トップレベルのアーキテクチャ設計
RAMは、我々がコントロールモジュールを使用して、読み書きメモリであるラムに読み出され、その後、書き込みデータ。
モジュールの機能
モジュール名 |
機能説明 |
Ram_control |
RAMコントローラ、my_ramに読み取りおよび書き込み |
My_ram |
RAMメモリIPコア |
RAM |
サブモジュールのカスケードを担当するトップレベルのモジュールシステム、 |
5 。3 。6ポートと記載インターコネクタ
トップレベルのモジュールのポートの説明
ポート名 |
ポート説明 |
CLK |
システムクロック入力 |
RST_N |
システムリセット |
Q |
データ出力 |
導入された内部配線システム
接続名 |
配線の手順 |
ADDR |
アドレス信号がRam_controlを生成しました |
データ |
生成されたデータをRam_control |
鷦鷯 |
Ram_control発生書き込み制御信号(ハイレベル、ローレベルの読み出しを書き込み) |
5. 3.7コード説明
Ram_controlのコードモジュール
/ ************************************************* *** *エンジニア: ドリーム・ブラザーウイング * QQ:761664056 *モジュールの機能:制御信号やデータを生成**************************************** ************* / 00 モジュール ram_control ( CLK 01 、 // システム・クロック入力 RST_N 02 、 // システムリセット WREN 03 、 // 信号の読み取りと書き込み ADDR 04 、 // アドレス信号 05データ// 有効なデータ 06 ); 07 // モジュール入力 08 INPUTの CLK ; // システム・クロック入力 09 INPUT RST_N ; // リセット 10 // モジュール出力 11 output reg wren; //读写信号 12 output reg [7:0] addr;//地址信号 13 output reg [7:0] data;//有效数据 14 //定义中间寄存器 15 reg state; //定义状态寄存器 16 17 always @ (posedge clk or negedge rst_n) 18 begin 19 if (!rst_n) // 复位时,将所有的输出清零。 20 begin 21 wren <= 0; 22 addr <= 0; 23 data <= 0; 24 state <= 0; 25 end 26 else 27 begin 28 case (state) 29 0 : begin 30 if (addr < 255)//使地址在0到255之间,让写信号有效 31 begin 32 addr <= addr + 1; 33 wren <= 1; 34 end 35 else 36 begin 37 addr <= 0;//转到下一个状态,让地址清零,让读信号有效 38 state <= 1; 39 wren <= 0; 40 end 41 42 if (data < 255)// 给有效数据,使数据在0到255之间 43 data <= data + 1; 44 else 45 data <= 0; 46 47 end 48 49 1 : begin 50 if (addr < 255)//使地址在0到255之间,让读信号有效 51 begin 52 addr <= addr + 1; 53 wren <= 0; 54 end 55 else 56 begin 57 state <= 0; //转到0状态,地址清零 58 addr <= 0; 59 end 60 end 61 62 default : state <= 0; // 如果系统不稳定的时候直接进入0状态 63 64 endcase 65 end 66 end 67 68 endmodule |
在本模块中,数据和地址的数值大小是一样的。
Ram的顶层代码
/**************************************************** * Engineer : 梦翼师兄 * QQ : 761664056 * The module function:顶层模块,负责连接各子模块 *****************************************************/ 00 module ram ( 01 clk, //系统时钟输入 02 rst_n,//系统复位 03 q //输出数据 04 ); 05 // 系统输入 06 input clk; //系统时钟输入 07 input rst_n;//系统复位 08 // 系统输出 09 output [7:0] q;//输出数据 10 //定义中间连线信号 11 wire wren; //定义写信号 12 wire [7:0] addr;// 定义地址信号 13 wire [7:0] data;//定义中间数据 14 // 调用ram_control 15 ram_control ram_control ( 16 .clk(clk), //系统时钟输入 17 .rst_n(rst_n), //系统复位 18 .wren(wren), //读写信号 19 .addr(addr), //地址信号 20 .data(data) //有效数据 21 ); 22 //调用IP核--ram 23 my_ram my_ram_inst ( 24 .address ( addr ), // 地址信号 25 .clock ( clk ), // 系统时钟 26 .data ( data ), // 输入数据 27 .wren ( wren ), //读写信号 28 .q ( q ) //输出数据 29 ); 30 31 endmodule |
本模块只负责连接各个子模块,没有任何的逻辑。代码编写完毕以后,查看RTL视图如下:
由RTL视图可以看出,电路综合以后的结果和我们所设计的系统框图一致,接下来编写测试代码如下:
/**************************************************** * Engineer : 梦翼师兄 * QQ : 761664056 * The module function:对ram进行测试 *****************************************************/ 00 `timescale 1ns/1ps //时间单位和精度定义 01 module ram_tb; 02 //系统输入 03 reg clk; //系统时钟输入 04 reg rst_n; //系统复位 05 //系统输出 06 wire [7:0] q; //输出数据 07 08 initial begin 09 clk = 1; 10 rst_n = 0; 11 # 200.1 12 rst_n = 1; 13 end 14 15 always # 10 clk = ~clk; //50MHz时钟 16 17 ram ram ( 18 .clk(clk), //系统时钟输入 19 .rst_n(rst_n), //系统复位 20 .q(q) //输出数据 21 ); 22 23 24 endmodule |
仿真分析
复位结束之后,写信号有效,同时给出数据和地址。Ram的q端在写的过程中也会进行慢一拍的输出,这不是错误,这是由Ram内部结构决定的。
注:写数据的过程中,q端也会输出,这是由altera RAM IP核的功能决定的,此处不需要深究。
当写完数据之后,进行读(写信号拉低),同时给出地址,ram在下一拍给出对应地址中的数据。
经过上述的分析,证明我们的ram应用正确。