RAM存储器详解:分类、特性及应用
RAM存储器详解:分类、特性及应用
RAM(随机存取存储器)是计算机系统中重要的存储组件,广泛应用于各种硬件设计中。本文将详细介绍RAM的分类、特性以及在逻辑设计中的应用,包括单端口RAM、伪双端口RAM和真双端口RAM的特点和使用场景,并通过具体的实例和代码解释了RAM读写冲突的处理方法。
RAM存储器概述
RAM是存储器分类的一个分支,属于静态存储器,RAM是逻辑设计中非常重要的一个特性。RAM一般包括单端口RAM(Single Port RAM)、双端口RAM设计(Two Port RAM)和真双端口RAM设计(Dual Port RAM)。
半导体存储器包括随机存储器和只读存储器。随机存储器RAM也包括静态RAM和动态RAM,其中动态RAM包括SDRAM、DDR SDRAM、DDR2 SDRAM、DDR3 SDRAM以及DDR4 SDRAM等。DDR SDRAM是目前非常流行也比较复杂的存储器,特点是容量非常大,速度也很高,掉电数据丢失。DDR SDRAM一般是单独的存储芯片。
静态RAM一般包括单端口RAM(Single Port RAM,缩写SP RAM,只有一个读写口,同一个时刻只能发起读或写),双端口RAM设计(Two Port RAM,缩写TP RAM,也叫伪双口,一个端口只能读,一个端口只能写),真双端口RAM设计(Dual Port RAM,缩写DP RAM,每个端口都可以进行读或者写操作)。特点是容量相对不是很大,速度非常高,掉电数据丢失。静态RAM在FPGA或者ASIC设计中都是非常重要的一个器件,可以说寄存器、组合逻辑和静态RAM构成了整个数字电路体系,足见静态RAM的重要性。
只读存储器包括PROM、EPROM、EEPROM等,目前EEPROM用的相对比较多,特点是容量相对较小,存储的一般是不易丢失的信息,比如网口或者USB 2.0芯片一般会配有一个EEPROM存储相关的固件信息。
几种RAM的特性和区别:
- 选择RAM时主要根据功能需求和带宽需求来选择,最合适的就是最好的。
- 如果需要读一个配置,这个配置只在上电的时候CPU配置一下就好了,其他的时候不需要写操作,那么直接选择单口RAM即可,只需要一个端口即可,要么是写操作,要么是读操作。
- 如果需要使用FIFO(先进先出存储器)来存储数据,就可以选择伪双口RAM即可,一个写口,一个读口,且读和写可以同时发生。
- 如果要实现一个对10000个车厢进行人数计数的功能,车厢有两个门,一个门只上车,一个门只下车,上车时候需要再原有人数基础上加一,下车时候需要在原有人数基础上减一,每个时刻都可能有人上车和下车,那么要使用逻辑统计这么多车厢的人数时,就需要有两个写端口的RAM,深度为10000,这个就需要使用真双端口RAM。因为如果使用寄存器资源进行统计,仅这个10000个车厢的计数就可能把FPGA寄存器资源耗尽。
RAM和FIFO的区别:
- RAM是指有地址线、数据线和使能的存储单元,可以通过地址对任意地址进行读写访问。FIFO也是一个端口只读,另一个端口只写。FIFO与伪双口RAM的区别在于,FIFO为先入先出,没有地址线,不能对存储单元寻址;而伪双口RAM两个端口都有地址线,可以对存储单元寻址;
- 使用场景不一样,FIFO一般放在传输带宽不一致的地方,用来吸收流量突发,而RAM一般用在需要根据地址进行写或者读的地方,比如存储一些配置信息。
单口RAM
单端口RAM指的是只有一个读写口,就是只有一组数据线和地址线,就是读和写都是通过这个口来访问RAM,但是同一个时刻只能访问一个,要么是读,要么是写。下图是一个Intel的单端口RAM模型。
Intel单端口RAM一般由如下信号构成:
- RAM还有一个重要的特性是RAM读延迟,就是RAM发起读,然后读数据有效的周期数。这个延迟一般是1,如果RAM输出再因为改善时序寄存一拍,那么RAM的读延迟就是2。如下所示,在读使能为1且地址有效的情况下(WEA为0 ENA为1),下一拍DOUTA即为读到的数据,一般来说,读使能和读地址不发生变化,DOUTA不会发生变化。
另外RAM读数据只使用RAM读有效时的读数据,没有发起读的时候,读数据一般不建议使用,因此此时的读数据依赖于RAM模型的特性,有可能是不确定的值。
伪双端口RAM
伪双端口RAM指的是有两个读写端口,但是一个端口只能读,一个端口只能写,伪双端口RAM一般叫TP RAM。一般FIFO内部例化的都是伪双端口RAM。
伪双端口RAM指的是有两个读写口,就是有两组数据线和地址线,一组是写数据线,一组是读数据线,同一个时刻写和读可以同时访问。下图是一个Intel的伪双端口RAM模型。
Intel伪双端口RAM一般由如下信号构成:
- RAM读延迟,就是RAM发起读,然后读数据有效的周期数。这个延迟一般是1,如果RAM输出再因为改善时序寄存一拍,那么RAM的读延迟就是2。如下所示,在读使能为1且地址有效的情况下(ENB为1),下一拍DOUTB即为读到的数据,一般来说,读使能和读地址不发生变化,DOUTB不会发生变化。
另外RAM读数据建议只使用RAM读有效时的读数据,没有发起读的时候,读数据一般不建议使用,因此此时的读数据依赖于RAM模型的特性,有可能是不确定的值。(与单端口RAM一致)
TP RAM有一个问题,就是读和写有两个端口,两个端口可以同时发起读和写,那么如果读和写同时有效且读和写是同一个地址时,此时读数据是否还是正确的数据呢,这个情况属于RAM读写冲突,属于逻辑设计中非常重要的一个特性处理。
一般设计中发起读写冲突,此时的读数据很可能是无效的读数据,因此一般读写冲突时候,会把最新的写数据直接赋给读数据,此时叫做写穿通到读。如下图所示:
从图中我们可以看出,Cycle 2读和写地址不同,读可以正常读到数据,但是到Cycle 3时,读和写地址相同且读写都有效,此处如果不做特殊处理,那么读数据是无效的。需要我们把写数据寄存一拍同步到读侧。
Verilog一般这样处理:先产生一个冲突信号,使用时序逻辑产生,读写冲突的下一拍有效,然后使用这个信号做判断,如果这个信号有效,则dout直接使用din_dly1(写数据寄存一拍的数据)赋值,否则使用q信号。
always @ (posedge clk or negedge rst_n) begin
if (rst_n == 1'b0)
conflict <= 1'b0 ;
else if ( wen && ren && (waddr == raddr ))
conflict <= 1'b1 ;
else
conflict <= 1'b0 ;
end
assign dout = conflict ? din_dly1 : q ;
真双端口RAM
下面我们来看下真双端口RAM。真双端口RAM指的是有两个独立的读写口,就是有两组数据线和地址线,一组是读或者写数据线,另外一组也是读或者写数据线,同一个时刻两个端口可以同时访问,两个端口可以是读和读,也可以是写和读,还可以是写和写。下图是一个Xilinx的真双端口RAM模型,Intel的真双端口RAM模型也是类似的,实际上ASIC中的真双端口RAM也是类似的。
真双端口RAM一般由如下信号构成:
DP RAM的读写冲突问题比TP RAM要复杂很多。为什么会复杂很多呢?这个是因为DP RAM的端口数比较多,所以冲突处理也比较复杂,不像TP RAM只有读和写冲突。如下表列出冲突组合情况:
其中端口A和B的读写冲突和TP RAM的情况完全相同,只不过有端口A和端口B发生读和写冲突和端口A和端口B发生写和读冲突两种情况,哪种情况处理都是需要把最新的写数据寄存一拍赋值给读数据,此处不再赘述。
DP RAM引入了一个写和写冲突,我们先来看下什么是写写冲突,写写冲突表示两个端口写写使能同时有效且写和写地址相同。
写写冲突发生时候,逻辑需要关断一个写,把两个写端口都需要更新的值处理到一个写端口上面。因为任何的DP RAM都不支持写和写冲突,如果发生了,那么最终的写数据就是不确定的值。
举个例子:有一个DP RAM A口为入向功能累加更新,假设每次累加2个,B口为出向功能递减更新,假设每次递减1个,那么正常情况下,每次都是A口读出之前的值,再加个2,然后回写回去。B口读出之前的值,再减个1,然后回写回去。但是当A和B发生写写冲突的时候,此时逻辑需要关断一个写,关断A口还是B口都是可以的,但是更新的值需要是处理后的值,处理后的值也就是先加2再减1,就是一个端口加1就可以了,另外一个端口不用回写。写写冲突发生的情况,如下图所示:
可以看出Cycle 3周期两个端口写写使能同时有效且写和写地址相同,发生写写冲突,此时逻辑需要做特殊处理,也就是把两个写端口都需要更新的值处理到一个写端口上面。如下图所示:
从图中我们可以看出,Cycle 2写和写地址不同,两个写端口不用特殊处理。Cycle 3时把两个写端口都需要更新的值处理到一个写端口上面,值更新A端口,B端口关断。