第1章:FIFO核心参数深度、宽度、空满标志、读写指针

各位同学好,我是老李。做芯片设计十几年了,FIFO这玩意儿几乎天天打交道。今天咱们聊聊FIFO最核心的几个参数。说白了,搞懂这些,你就能看懂大部分FIFO设计。

1.1 深度(Depth)——你到底能存多少数据?

深度,就是FIFO能存多少个数据条目。我习惯叫它“槽位”。比如深度16,就是有16个槽位。

深度怎么定?这得看你的应用场景。我在一个视频处理项目里遇到过,写入端是摄像头,每秒30帧,读出端是显示控制器。写入快,读出慢,中间就得靠FIFO缓冲。深度不够,数据就丢了。

核心公式:

深度 ≥ (写入速率 - 读出速率) × 最大突发时间

说白了,就是算清楚“最坏情况下”你会多出多少数据没地方放。

我的经验:深度别卡太死。留20%余量,省得后期改设计。我曾经因为深度少算了2个,导致芯片重做,那叫一个心疼。

1.2 宽度(Width)——一次能搬多少比特?

宽度就是每个槽位能存多少比特。8位、16位、32位、64位,常见就这些。

宽度选择其实挺直观的:你的数据总线多宽,FIFO宽度就设多宽。但有个坑——读写宽度可以不一样。比如写入是8位,读出是32位。这种叫“异步宽度转换FIFO”。

应用场景 推荐宽度 说明
CPU与低速外设通信 8位或16位 匹配外设接口
高速数据采集 32位或64位 提高吞吐量
网络数据包处理 64位或128位 匹配MAC层

注意:宽度越大,面积越大。每增加1位宽度,存储面积就线性增长。你想想看,深度1024、宽度128的FIFO,光存储阵列就吃掉不少芯片面积。

1.3 空满标志(Empty/Full)——FIFO的“红绿灯”

空满标志是FIFO的灵魂。没有它,你根本不知道什么时候该读、什么时候该写。

空标志(Empty):FIFO里没数据了,读操作会读到无效数据。
满标志(Full):FIFO里塞满了,写操作会覆盖旧数据。

为什么会这样?因为读写指针在转圈圈。嗯,这里要注意——空满判断是异步FIFO里最容易出错的地方。

判断逻辑:

  • 空:读指针追上写指针(两者相等)
  • 满:写指针追上读指针(差一个周期)

但实际设计时,得用格雷码处理跨时钟域,不然会出毛刺。

我记得有一次调试,满标志老是不对。查了三天,发现是格雷码转换时少打了一拍。从那以后,我所有异步FIFO的满标志都至少打两拍再输出。

1.4 读写指针(Read/Write Pointer)——FIFO的“导航员”

读写指针就是两个计数器。写指针指向下一个要写入的地址,读指针指向下一个要读出的地址。

指针怎么转?写一次,写指针加1;读一次,读指针加1。到了深度边界,就绕回0。这就是“环形缓冲区”的概念。

// 伪代码示例
always @(posedge clk) begin
    if (write_enable && !full)
        write_ptr <= write_ptr + 1;
    if (read_enable && !empty)
        read_ptr <= read_ptr + 1;
end

// 空满判断
assign empty = (write_ptr == read_ptr);
assign full  = (write_ptr[WIDTH-1:0] == read_ptr[WIDTH-1:0]) && 
               (write_ptr[WIDTH] != read_ptr[WIDTH]);

我的习惯:指针宽度比深度多1位。比如深度16,指针就用5位。多出的1位用来区分空和满。这样判断逻辑简单,不容易出错。

1.5 四个参数的关系——一张图看懂

下面这张图,是我画了无数遍才总结出来的。它展示了深度、宽度、空满标志、读写指针之间的关系。

FIFO存储阵列 深度(Depth)= N个槽位 宽度(Width)= M位 写指针(WPTR) 读指针(RPTR) 空/满标志 每个槽位存储M位数据 共N个槽位

你看,写指针和读指针在存储阵列里“赛跑”。空满标志就是裁判,告诉你谁领先了。宽度决定了每个槽位能装多少数据,深度决定了总共有多少槽位。

1.6 面积功耗权衡——我的实战心得

做FIFO设计,最头疼的就是面积和功耗的平衡。我总结了几条经验:

  • 深度越大,面积越大,功耗也越大。每增加一倍深度,存储面积翻倍。如果功耗敏感,考虑用SRAM代替寄存器阵列。
  • 宽度越宽,面积越大。但宽度对功耗影响相对小,因为读写操作次数不变。
  • 空满标志的生成逻辑,用组合逻辑面积小但时序差,用寄存器打拍面积大但时序好。我一般选后者,省得后期修时序。
  • 读写指针用二进制计数器面积最小,但跨时钟域需要格雷码转换。格雷码计数器面积大20%左右,但安全。

避坑指南:我曾经在一个低功耗项目里,为了省面积用了深度512的寄存器FIFO。结果功耗超标30%。后来换成SRAM,面积小了40%,功耗降了50%。所以,深度超过64,我建议用SRAM。

好了,这一章就到这里。四个参数——深度、宽度、空满标志、读写指针——是FIFO设计的基石。你想想看,搞懂了它们,是不是觉得FIFO也没那么神秘了?

可可精品资料库