RAM IP核配置

作者 : admin 本文共4524个字,预计阅读时间需要12分钟 发布时间: 2024-06-17 共1人阅读

REVIEW

之前已经学习过:

ROM:FPGA寄存器 Vivado IP核-CSDN博客

串口接收:Vivado 串口接收优化-CSDN博客

1.  今日摸鱼计划

RAM创建与测试

小梅哥视频:

21C_嵌入式块存储器RAM介绍_哔哩哔哩_bilibili

21D_嵌入式块存储器RAM实现和仿真_哔哩哔哩_bilibili

小梅哥教材:

02_【逻辑教程】基于HDL的FPGA逻辑设计与验证教程V3.4.pdf

        14 IP 核使用之
RAM

2.  RAM IP核配置

RAM(Random Access Memory):
RAM是一种计算机主存,用于临时存储数据和程序。

它可以随时把数据写入到任何一指定地址的存储单元,也可以随时从任一指定地址读出数据。

其读写速度有时钟频率决定,主要用来存放程序以及程序执行过程中产生的数据运算结果等。

RAM IP核配置插图

RAM IP核配置插图(1)

Distributed Memory Generator
生成的 ROM/RAM Core
占用的资源是
LUT

(查找表,查找表本质就是一个小的
RAM

 Block Memory Generator

生成的
ROM/RAM Core
占用的资源是 Block Memory

(嵌入式的硬件
RAM

RAM IP核配置插图(2)

RAM IP核配置插图(3)

RAM
:单端口
RAM
、简单双端口
RAM 和真双端口 RAM

具体的差异我们可以通过依次选择,然后观察窗口左边
RAM 端口来进行对比

单端口
RAM
读写一个时钟,读写不能同时进行。

RAM IP核配置插图(4)

简单双端口
RAM

相较单端口
RAM
,多出一个
PORTB,有两个时钟,可以同时读写,

PORTA
只能写数据,
PORTB
只能进行读数据。

RAM IP核配置插图(5)

真双端口
RAM

两个
PORT
,分别有自己的时钟、地址、输入/输出数据端口,两个端口均可进行读写操作。

RAM IP核配置插图(6)

写数据字节使能:
如果勾选,写使能信号会根据写数据的字节数生成对应的
bit
数据,
1
个字节对应
1bit
写使能,这里字节的大小可以设置为
8

9,当这里选择后,输入输出的数据的位宽就必须是
8

9 的整数倍,这里我们需要一个位宽为
8bit

RAM
,这里勾选
Write Enable
并设置字节大小为
8bit

RAM IP核配置插图(7)

算法类型
有三种选项可选,最小面积、低功耗、固定原语。这里不过多讲解,需要了解更多的可以查阅
IP
手册,
IP
手册上面
42页开始有对这个详细的讲解。这里我们保持默认的最小面积选项即可。

RAM IP核配置插图(8)

RAM IP核配置插图(9)

操作模式设置:
有三个可选项,主要是针对在同时对同一地址进行读操作和写操作时,读出数据是写入的最新数据、该地址原来的数据、读数据不变化。

Write First 模式下的波形,如果仅读出数据而未发生数据的同时读写,则读出存储器以前存储的数据,如果发生数据的同时读写,读出数据为刚从数据总线送入的数据,而不考虑该地址以前存储的数据。

RAM IP核配置插图(10)

Read First 模式下的波形,同时对同一地址读写,读出数据为上次刚写入该地址以前的数据,忽略正在写数据这一事件对读出数据的影响。

RAM IP核配置插图(11)

No Change 模式下波形,读出的数据只有在进行读操作但未进行写操作时更新数据,在同时读写数据时,读出数据保持不变。

RAM IP核配置插图(12)

端口使能信号
类型设置,一个是一直使能,一个是通过一个
ENA 信号管脚控制,这里选择
Always Enable

RAM IP核配置插图(13)

RAM IP核配置插图(14)

端口B输出寄存器配置:

这里可以看下
RAM内部结构图,可以很清楚的看到
Primitives Output Register
是结构中的
1
处的寄存器,
Core Output Register 是结构图中
2
出的寄存器。

REGCEB Pin 是寄存器使能管脚,如果勾选,会有一个寄存器使能控制管脚用于控制寄存器的使能,如果不勾选寄存器就一直使能状态,这里就不勾选。

要得到更好的性能,将这里的两个寄存器都勾选。

RAM IP核配置插图(15)

端口 B 输出置位/复位设置

这里不创建置位
/
复位端口,需注意这里置位/复位并不复位
RAM
中的数据而是只复位寄存器上的值。

RAM IP核配置插图(16)

其它保持默认就OK

最后看一看总的情况,信息包括使用的资源,
A

B 端口的地址位宽,以及端口
B Read Latency

3
个时钟周期。

RAM IP核配置插图(17)

Latentcy
指的是相对于某个时钟起始位的
1 个或多个时钟后数据才有效,一般以时钟为单位,这里表示的是时钟采集到读数据地址到数据有效的时间间隔,举例子说明:

RAM IP核配置插图(18)

RAM IP核配置插图(19)

RAM IP核配置插图(20)

这里之所以
Latency 等于 3
,是因为我们前面配置同时勾选了 Primitives Output Register

Core Output Register
,相当于数据打了两拍。

到这里
IP
设置就完成了,点击
OK
,点击
Generate
生成
IP

RAM IP核配置插图(21)

3.  RAM 测试

`timescale 1ns/1ns
`define CLKA_PERIOD 20
`define CLKB_PERIOD 30

module ram_tb();
        reg clka;
        reg wea;
        reg [7:0]addra;
        reg [7:0]dina;
        reg clkb;
        reg [7:0]addrb;
        wire[7:0]doutb;
        integer i;
        blk_mem_gen_0 blk_mem_gen_0_ (
                                     .clka(clka), // input wire clka
                                     .wea(wea), // input wire [0 : 0] wea
                                     .addra(addra), // input wire [7 : 0] addra
                                     .dina(dina), // input wire [7 : 0] dina
                                     .clkb(clkb), // input wire clkb
                                     .addrb(addrb), // input wire [7 : 0] addrb
                                     .doutb(doutb) // output wire [7 : 0] doutb
                                    );

        //blk_mem_gen_0 是忘记改名字哩~
        //配置时钟信号 clka  clkb                         
        initial clka = 1’b1;
        always #(`CLKA_PERIOD/2) clka = ~clka;
        initial clkb = 1’b1;
        always #(`CLKB_PERIOD/2) clkb = ~clkb;
        
        initial
            begin
                wea = 0;
                addra = 0;
                dina = 0;
                addrb = 255; //255
                #(`CLKA_PERIOD*10 +1 );
                wea = 1;   //写使能信号,高电平写入
                    for (i = 0 ; i< 32 ; i = i+1)begin
                        dina = 127 – i;
                        addra = i;
                        #`CLKA_PERIOD;
                    end
                wea = 0;
                #1;
                    for (i = 0 ; i < 32 ; i = i+1)begin
                        addrb = i;
                        #`CLKB_PERIOD;
                    end
            #200;
            $stop; 
            end
endmodule

RAM IP核配置插图(22)

本测试,对RAM 地址0~31 写入127~96

然后从地址0~31依次读取其中的数值

RAM IP核配置插图(23)

RAM IP核配置插图(24)

这里可以看到读取时,会晚3个时钟周期

本次RAM读写都未配置使能ena enb 所以看起来很简单;

(但是本摸鱼怪又觉得没有使能控制看着有点怪,后边再搞一下呗~)

4.  带使能en的RAM

RAM IP核配置插图(25)

RAM IP核配置插图(26)
RAM IP核配置插图(27)
ram_tb

`timescale 1ns/1ns
`define CLKA_PERIOD 20
`define CLKB_PERIOD 30

module ram_tb();
        reg clka;
        reg ena ;
        reg wea;
        reg [7:0]addra;
        reg [7:0]dina;
        reg clkb;
        reg enb ;
        reg [7:0]addrb;
        wire[7:0]doutb;
        integer i;
        
        ram_8 ram_8_ (
                                     .clka(clka), // input wire clka
                                     .ena(ena),
                                     .wea(wea), // input wire [0 : 0] wea
                                     .addra(addra), // input wire [7 : 0] addra
                                     .dina(dina), // input wire [7 : 0] dina
                                     .clkb(clkb), // input wire clkb
                                     .enb(enb),
                                     .addrb(addrb), // input wire [7 : 0] addrb
                                     .doutb(doutb) // output wire [7 : 0] doutb
                                    );

        
        //配置时钟信号 clka  clkb                         
        initial clka = 1’b1;
        always #(`CLKA_PERIOD/2) clka = ~clka;
        initial clkb = 1’b1;
        always #(`CLKB_PERIOD/2) clkb = ~clkb;
        
        initial
            begin
                ena = 0 ;
                wea = 0;
                addra = 0;
                dina = 0;
                enb = 0;
                addrb = 255; //255
                #(`CLKA_PERIOD*10 +1 );
                ena = 1;
                wea = 1;   //写使能信号,高电平写入
                    for (i = 0 ; i< 32 ; i = i+1)begin
                        dina = 127 – i;
                        addra = i;
                        #`CLKA_PERIOD;
                    end
                wea = 0;
                ena = 0;
                #1;
                enb = 1;
                    for (i = 0 ; i < 32 ; i = i+1)begin
                        addrb = i;
                        #`CLKB_PERIOD;
                    end
                
            #60;
            enb = 0;
            #200;
            $stop; 
            end
endmodule

RAM IP核配置插图(28)
#60;
enb = 0;

这个自己调试一下就会发现问题

(其实就是Latentcy

本摸鱼怪还是行动力很强的嘛,桀桀桀~~~

本站无任何商业行为
个人在线分享 » RAM IP核配置
E-->