[FPGA深度解析]异步FIFO原理及使用

本文详细介绍了异步FIFO的工作原理、与同步FIFO的区别、设计思想及其关键技术,如地址采样时钟问题、格雷码的应用。重点探讨了跨时钟域同步和空满状态判断,以及FIFO深度的计算方法。通过实例解释了如何避免地址回卷问题,确保FIFO操作的正确性。
摘要由CSDN通过智能技术生成

1.异步FIFO的原理

FIFO是一种数据缓冲器,用来实现数据先入先出的读/写方式。FIFO有一个写端口和一个读端口,外部无需使用者控制地址,使用方便。FIFO与普通的Block RAM有一个很明显的区别就是使用Block RAM来做数据缓存处理,使用者必须自己控制读和写地址的管理,必须保证写的数据不把Block RAM中未被读出的内容覆盖掉从而造成数据错误,同时保证读的时候要读出未被写入的地址。而采用FIFO时,只需要关注FIFO控制器给出的空满状态信号即可知道当前有没有错误的操作了FIFO,使FIFO的数据写溢出或读空。

2.同步FIFO与异步FIFO的区别

同步FIFO是指读时钟和写时钟为同一个时钟。
异步FIFO是指读/写时钟不一致,是相互独立的。数据是由某一个时钟写入FIFO,而由另一个时钟域的控制信号将数据读出FIFO。也就是说,读/写指针的变化动作是由不同的时钟产生的。
异步FIFO的重要参数有:时钟、数据位宽、深度、读/写指针、空满指针和RAM的大小。
(1)写时钟(wrclk):该时钟为异步FIFO写操作的工作时钟。
(2)读时钟(rdclk):该时钟为异步FIFO读操作的工作时钟。
(3)FIFO的数据位宽(bit width):就是FIFO一次读/写操作的数据位,其数据位宽根据设计需要进行定义。
(4)深度(depth):在FIFO实际工作中,其数据的空/满标志可以控制数据的继续写入或读出,故实际中用到的FIFO要根据电路的具体情况,在兼顾系统性能和FIFO的成本的情况下估算一个大概的宽度和深度就可以了。指FIFO中可以存储多少个N位的数据(假设宽度为N)。
(5)满标志(full):FIFO已满或将要满时,由FIFO的状态电路送出一个信号,从而阻止FIFO的写操作继续向FIFO中写数据造成的溢出(Overflow)。同时,使用者可根据这个信号来做出相应的处理。
(6)空标志(empty):FIFO已空或将要空时,由FIFO的状态电路送出一个信号,从而阻止FIFO的读操作继续从FIFO中读出数据而造成无效数据的读出。
(7)将满信号(almost full):
(8)将空信号(almost empty):
(9)读写指针:就是读写地址,只不过这个地址不能任意选择,而是连续的关系,其写指针减读指针得到FIFO中所含的数据个数
(10)RAM:常用的RAM包括单口RAM、简单双口RAM、真双口RAM、单口ROM、双口ROM这五种类型的RAM,可以使用简单双口RAM来做FIFO内部的RAM,也可以使用寄存器来实现FIFO的存储器。寄存器实现的方式比较合适深度和位宽较小的情况,一般在FPGA中还是推荐使用Block RAM来实现异步FIFO的存储器。

3.异步FIFO设计思想

异步FIFO基本上分为6个部分,分别是写时钟域的地址管理读时钟域的地址管理读时钟域读地址到写时钟域的格雷码同步写时钟域写地址到读时钟域的格雷码方式同步写时钟域的满和将满信号的产生读时钟域的空和将空信号的产生
复位后,读和写地址指针均指在0地址处,同时almost empty和empty信号均有效。在写时钟域,当用户的写请求wren有效时,如果此时的写时钟域的状态正常(即还未满),则RAM写使能信号wr_ram有效,数据将会写入RAM中,同时在下一个clk原来的写地址加1,指向下一个写地址。
读时钟域侧,当用户的读请求rden有效,数据将会从RAM里被读出,同时在下一个clk原来的读地址加1,指向下一个读地址。
在写时钟域FIFO状态的判断及产生是使用了一种叫格雷码同步的方法实现多比特跨时钟域的转换、把读地址从读时钟rd_clk同步到wr_clk,然后判断写地址和读地址之间的差从而判断FIFO是否被写满。在读时钟域FIFO状态判断及产生也使用了格雷码同步的方法实现多比特跨时钟域的转换、把写地址从写时钟wr_clk到rd_clk的转换,然后判断写地址和读地址之差进而得出FIFO是否为空的结论。
FIFO本身空满信号产生的判断方式也有一定的技巧, 因为FIFO是一种回卷式的写和读, 假设FIFO的深度为1024,在T0时刻写地址第一次写的时候是从0地址开始写起,假设在T1时刻写到地址512的时候发生了读操作,在T2时刻写到1023的时候读地址指针来到了地址256,那么如果继续写的话又将出现从0地址开始写的情况,因为这时候地址0到地址255的数据已经被读走,在接下来的下一个时钟周期将会出现写地址在0的情况。
为了解决这一回卷的问题,将使用的地址宽展到11位,即wraddr[10:0]和raddr[10:0], 这是为了方便1024的判断以及处理写、读回卷问题。当读写地址相同时,即wraddr与raddr相等,此时为空;如果wraddr的最高位和raddr的最高位不同,但是其余位都相同,那就是FIFO满。
异步FIFO设计的重点:
第一点: 跨时钟域的转换及同步,因为FIFO的地址是逐1递增的,因此在做跨时钟域转换的时候可以把按照逐1递增的地址编码成每次只变化一位的格雷码,实现对数据跨时钟域直接采集。如果跨时钟域的数据每次只能改变一位,那么可以用但比特跨时钟域同步的方法直接采样,这种方式是安全的。即,将二进制码转换为格雷码,然后在目的的时钟域被采集
第二点: 状态信号的产生相对保守的方式。在做空、满等信号的时候,采用保守做法。即如果系统即将为空或者满,信号一定会有效,而且可能还会提前出现。另外,空或者满是禁止对FIFO进行操作的,这样可以保证对FIFO操作正常。

4.异步FIFO读/写地址采样

4.1 异步FIFO读/写采样时钟问题

在异步FIFO的设计中,读/写的时钟是分开的,因此必须将工作于读时钟的读地址指针同步过来,并作为FIFO的满状态判断;同样,必须将工作于写时钟的写地址指针同步过来,并作为FIFO的空状态判断。由于读/写时钟是异步的,此时就涉及到一个跨时钟域问题,如果直接拿读/写地址来用会出现误判。

4.2 格雷码的引用

FIFO的读/写地址在写入或者读出数据时都是逐1递增的,即从地址0、地址1、地址2…因此可以考虑把该二进制转换成每次只跳变一个比特的格雷码,然后再另一个时钟域对该格雷码进行采样。由于同步前只有一比特的信号可能被错误采样,而一比特的错误采样只会导致一个单位地址的判断错误,不会带来FIFO状态误判的影响。
因此,在FIFO中,地址总线可以先转换为Gray码,然后用双D触发器对Gray码地址进行同步,其误码概率与单比特信号的跨时钟域转换是一致的。
Gray码相邻两个加一地址之间永远只有一个比特的变化,如果异步时钟刚好在地址跳变的时刻采样Gray编码,即便数据不稳定,但译码后错误的偏差只是1,设计时判断FIFO深度、满空等留较小的余量就可以满足要求。
Gray码可以有效的解决异步FIFO读/写地址采样不稳定的问题,提高系统的可靠性;缺点是有延迟(可提前判断来补偿),电路门数、复杂度增加。 但是,用Gray编码来解决该问题也是异步FIFO设计最常用的方法。

4.3 格雷码的编码原理

二进制码到格雷码的映射方式为将原二进制码左移一位,高位补零,然后与原二进制码进行异或即可。
G r a y n = B n ⊗ B n + 1 ⊗ … ( n = 0 , 1 , … , N − 2 ) . G r a y n = B n … ( n = N − 1 ) . Gray_n = B_n \otimes B_{n+1} \otimes \ldots (n = 0,1,\ldots ,N - 2). \\Gray_n = B_n \ldots (n =N - 1). Gra

  • 13
    点赞
  • 72
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值