ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

FPGA 异步 FIFO 乒乓缓存设计:连续采集数据如何完整交给 USB

FPGA 异步 FIFO 乒乓缓存设计:连续采集数据如何完整交给 USB FPGA 异步 FIFO 乒乓缓存设计:连续采集数据如何完整交给 USB系列文章:这是「基于 FPGA 和 USB2.0 接口的 CCD 光谱信号采集系统」的数据通路专题之一。上一篇讲 CCD 与 ADC 如何形成采样窗口;本文只聚焦采样数据进入 FPGA 后,怎样通过双异步 FIFO 以“整帧交接”的方式送往 USB。文中图片根据当前 RTL 重绘,附上完整源码仅作审核分享讨论。摘要在连续采集场景中,采集端不会因为 USB 暂时不能接收就停下来,而 USB 的读数节奏又受接口就绪和上位机接收影响。把采样数据直接连到 USB,看起来链路最短,却很容易在帧边界处出现覆盖、错位或不完整数据。本项目采用“16 位数据格式化 + 双异步 FIFO + A/B 乒乓调度”的方式:采集侧把一帧数据写入 A 或 B;帧结束后,控制器把已封帧的一块交给读取侧,同时把下一帧写入另一块。FIFO 写口使用采集/写入时钟域,读口使用 USB 60 MHz 时钟域,从而把数据跨域和帧级所有权切换分开处理。本文结合ccd_tra_v3.8中的fifo_drive.v、data_12_16.v和 FIFO IP 配置,讲清楚这套缓存为什么这样划分、当前 RTL 怎样工作,以及一个可复用设计还应补哪些保护。1. 为什么不能让采集端“等一等 USB”数据通路有两种完全不同的节奏:采集侧:数据有效窗口一旦开始,样本按采样时钟连续产生 USB 侧:只有接口满足就绪条件时,才允许取走下一个字节如果两端直连,USB 的一个短暂停顿就会直接传导到采集侧;而采集侧的样本不等人,后果往往不是“少一个数字”这么简单,而是帧头、帧尾或像素位置被破坏。对于后续的光谱/图像重建,这类错位很难靠软件补救。FIFO 先把写入和读取隔开:写端只管接住采样数据,读端只在 USB 可取数时读。进一步使用两块 FIFO,则把“当前正在写的一帧”和“上一帧的发送”分给两块独立的缓冲区。2. 本文这块数据通路到底包含什么当前工程的相关顶层连接可以概括为:CCD/ADC 采样窗口 │ ccd_data[13:0] + ad_flag ▼ data_12_16:帧头、有效数据、帧尾 → data_16[15:0] │ ├── FIFO A:16 位写入 / 8 位读出 ──┐ └── FIFO B:16 位写入 / 8 位读出 ──┤→ USB 读取侧 ▲ │ └──── fifo_drive ─────┘先强调一个容易混淆的点:这里不是“四通道 ADC 轮流串行化”。当前 RTL 中,data_12_16的职责是把 14 位 CCD 采样数据包装为 16 位字,并插入0xAAAA帧头与0x5555帧尾;FIFO IP 再把 16 位写入数据转换为 8 位读出数据。这样后级可以按字节流读取,同时仍保留可识别的帧边界。实际的数据字顺序如下:ad_flag 上升沿 → 0xAAAA(帧头) ad_flag 有效期 → 00 + ccd_data[13:0](一个 16 位样本字) ad_flag 下降沿 → 保留最后一个样本字 下一状态 → 0x5555(帧尾)因此,FIFO 缓存的不只是“ADC 数值”,而是一段后端能够自检帧边界的字流。以后分析上位机收到的数据时,除了检查样本数,还应检查帧头、帧尾是否成对出现、它们之间的长度是否符合预期。环节当前工程中的实现要解决的问题数据格式化data_12_16把帧头、14 位有效样本与帧尾组织成 16 位数据流。时钟域隔离两个fifo_temp异步 FIFO 实例写侧与 USB 60 MHz 读侧不需要同频同相。乒乓调度fifo_drive一块写满一帧后交给读取端,另一块接下一帧。USB 门控fifo_rdreq_a/b只在选中的 FIFO 非空且 USB 条件允许时发起读取。3. 设计的关键:不是“交替写”,而是“封帧后交接”乒乓缓存最核心的设计思路,是把一帧的完成状态变成缓冲区的所有权边界。
返回列表