背景
不管从事FPGA哪个方面避免不了使用FIFO,充当缓存,多bit数据跨时钟处理等。
说来惭愧,我长期使用的是Xilinx提供FIFO的IP核,认为有现成的为啥不用。直到后来觉得FIFO问题其实在笔试还是面试中都会被提及
所以决定写以此文,自己的看法,如有不对之处,请批评指出。
前提
首先我们来考虑2种场景
①:假如模块A不间断的往FIFO中写数据,模块B同样不间断的从FIFO中读数据,不同的是模块A写数据的时钟频率要大于模块B读数据的时钟频率,那么在一段时间内总是有一些数据没来得及被读走,如果系统一直在工作,那么那些没有被读走的数据会越累积越多,那么FIFO的深度需要是无穷大的。(所以FIFO常判断依据是空满信号,有的是自定义阈值空满)
②:因此只有在突发数据传输过程中讨论FIFO深度才是有意义的。什么是突发传输,简单的理解是FIFO的最小深度就等于没有被读走的数据个数。
假设情况
第一种:
CLKW>CLKR
CLKW = 100Mhz
CLKR = 50Mhz
BL(burst length)=120 (两个package之间时间足够长)
width = 8bit
求FIFO最小深度
分析:
- 写一个数据所需要的时间 = 1/100MHz = 10.0ns
- 突发传输中,写完所有数据所需要的时间 = 120*10.0ns = 1200ns
- 读一个数据所需要的时间 = 1/50MHz = 20ns
- 所以写完所有的突发传输数据需要花费1200ns
- 在1200ns内能够读走的数据个数 = 1200ns/20ns = 60
- 所以在1200ns内还没有被读走的数据个数 = 120-60 = 60
- 因此FIFO的最小深度为60(由于是2的n次幂,所以应该是64)
第二种:
CLKW>CLKR
CLKW = 100Mhz
CLKR = 50Mhz
BL(burst length)=120 (
每隔1个clk写一次
每隔3个clk读一次
)
width = 8bit
求FIFO最小深度
分析:
- 每隔1个cycle写一次,意味着2个clk才写一个数据
- 每隔3个cycle读一次,意味着4个clk才读一个数据
- 写一个数据所需要的时间 = 2*1/100MHz = 20ns
- 突发传输中,写完所有数据所需要的时间 = 120*20ns = 2400ns
- 读一个数据所需要的时间 = 4*1/50MHz = 80ns
- 所以写完所有的突发传输数据需要花费2400ns
- 在2400ns内能够读走的数据个数 = 2400ns/80ns = 30
- 所以在2400ns内还没有被读走的数据个数 = 120-30 = 90
- 因此FIFO的最小深度为90(由于是2的n次幂,所以应该是128)
第三种:
CLKW<CLKR
CLKW = 40Mhz
CLKR = 50Mhz
BL(burst length)=120 (
每隔1个clk写一次
每隔3个clk读一次
)
width = 8bit
求FIFO最小深度
分析:
- 每隔1个cycle写一次,意味着2个clk才写一个数据
- 每隔3个cycle读一次,意味着4个clk才读一个数据
- 写一个数据所需要的时间 = 2*1/40MHz = 50ns
- 突发传输中,写完所有数据所需要的时间 = 120*50ns = 6000ns
- 读一个数据所需要的时间 = 4*1/50MHz = 80ns
- 所以写完所有的突发传输数据需要花费6000ns
- 在2400ns内能够读走的数据个数 = 6000ns/80ns = 75
- 所以在2400ns内还没有被读走的数据个数 = 120-75 = 45
- 因此FIFO的最小深度为45(由于是2的n次幂,所以应该是64)
第四种:
CLKW=CLKR
CLKW = 50Mhz
CLKR = 50Mhz
BL(burst length)=120 (
每隔1个clk写一次
每隔3个clk读一次
)
width = 8bit
求FIFO最小深度
分析:
- 每隔1个cycle写一次,意味着2个clk才写一个数据
- 每隔3个cycle读一次,意味着4个clk才读一个数据
- 写一个数据所需要的时间 = 2*1/50MHz = 40ns
- 突发传输中,写完所有数据所需要的时间 = 120*40ns = 4800ns
- 读一个数据所需要的时间 = 4*1/50MHz = 80ns
- 所以写完所有的突发传输数据需要花费6000ns
- 在2400ns内能够读走的数据个数 = 4800ns/80ns = 60
- 所以在2400ns内还没有被读走的数据个数 = 120-60 = 60
- 因此FIFO的最小深度为60(由于是2的n次幂,所以应该是64)
第五种:
CLKW>CLKR
CLKW = 80Mhz
CLKR = 50Mhz
在写时钟周期内,每100个周期就有40个数据写入FIFO
在读时钟周期内,每10个周期可以有8个数据读出FIFO
width = 8bit
求FIFO最小深度
分析
- 首先这里没有给出数据的突发长度,从假设中可以得出每100个周期就有40个数据写入FIFO,这里可能就有人会说突发长度就是40个数据,其实不是这样的,因为数据是随机写入FIFO的,我们需要考虑做坏的情形,即写速率最大的情形,只有如下图背靠背的情形才是写速率最高的情形,burst length为80
- 注意:这里需要验证一下是否有解,即写入burst数据时间必须大于等于读出burst数据时间,不然数据就会越累积越多,使得FIFO的深度必须为无穷大。
- 首先写入80个数据需要的时间 = 1/80MHz*(80*100/40)=2500ns(由80/(40/100)*1/80得来【40/100表示每个数据花费的周期,一共80个数据,求出80个周期】),读出80个数据需要的时间 = 1/50MHz*(80*10/8)=2000ns,由于写入burst数据时间大于对出burst数据时间,因此有解。
- 下面来计算FIFO最小深度,连续写入80个数据最快所需要时间 = 1/80MHz * 80 = 1000ns
- 从FIFO中读出一个数据至少所需时间 = (1/50MHz) * (10/8) = 25ns
- 那么在1000ns内能够读出的数据 = 1000ns/25ns = 40
- 在1000ns内没有读出的数据 = 80 - 40 = 40
- 因此FIFO的最小深度为40
总结
从上面分析来看,求FIFO的最小深度主要有以下要点:
- 在求解之前需要验证一下在允许的最大时间长度内写入的数据量是否等于读出的数据量,保证有解;
- 求FIFO深度需要考虑最坏的情形,读写的速率应该相差最大,也就是说需要找出最大的写速率和最小的读速率;
- 不管什么场景,要确定FIFO的深度,关键在于计算出在突发读写这段时间内有多少个数据没有被读走;
- 由于FIFO空满标志位的判断延迟,在实际应用中需要预留一些余量。
下面我们来推导一下FIFO深度的求解公式,假设:
- 写时钟频率为fwr
- 读时钟频率为frd
- 在写时钟周期内,每m个周期内就有n个数据写入FIFO
- 在读时钟周期内,每x个周期内可以有y个数据读出FIFO
那么:
- 首先必须满足(1/fwr)*(m/n) ≥ (1/frd)*(x/y)
- ”背靠背“的情形下是FIFO读写的最坏情形,burst长度 B = 2*n
- 写完burst长度数据最快所需时间 T = (1/fwr) * B
- 从FIFO中读出一个数据至少需要时间 t= (1/frd) * (x/y)
- 在T时间内能够从都走的数据个数 = T/t = B * (frd/fwr) * (y/x)
- 在T时间内还没有读走的数据个数 = B - B * (frd/fwr) * (y/x)
- 因此FIFO的最小深度为 B - B * (frd/fwr) * (y/x)
- 注意保留一些余量
FIFO深度计算
原文:https://www.cnblogs.com/FPGA-Jenson/p/13695979.html