FPGA之FIFO详解,读写位宽不同
这篇博客里,通过两个练习来总结在FPGA设计中FIFO读写位宽不同的情况下,我们应该去如何设计时序逻辑,因为在现实工程中FIFO读写位宽不同也是经常出现的情况。
练习1
设计一个模块包含读写位宽是32bit、读写深度是64的异步时钟FIFO,其中输入数据信号din和输入 数据指示信号din_vld是属于clk_in时钟域的,上游模块会负责写数据到本模块的FIFO中,当本模块FIFO写端口已写入了60个数据,也就是FIFO快要写满溢出的时候,这时上游模块仍有数据要写入FIFO则直接丢弃该数据。下游模块负责从本模块的FIFO中读数据,当下游模块输入rdy信号时表示下游模块已准备好可以接收FIFO中的数据了,这时如果FIFO中有数据,那么就把FIFO中的数据赋值给输出数据信号dout送至下游模块并同时拉高dout_vld输出数据指示信号,其中输出数据信号dout和输出数据指示信号dout_vld则是属于clk_out时钟域的,上游模块din信号的写位宽是32bit,下游模块dout信号的读位宽是8bit,表1为练习1的信号列表。
信号列表 |
||
信号名 |
I/O |
位宽 |
clk_in |
I |
1 |
rst_n |
I |
1 |
rdy |
I |
1 |
din |
I |
32 |
din_vld |
I |
1 |
clk_out |
I |
1 |
dout |
O |
8 |
dout_vld |
O |
1 |
fifo_empty |
O |
1 |
表1 FIFO IP练习1设计中的信号列表
我们来思考下练习1功能模块的代码设计,其实不同的地方主要在于上游模块的写位宽din是32bit,而下游模块的读位宽dout是8bit,两者位宽是不一致的,同样的方法我们也在Vivado下初始化一个读写位宽是32bit、读写深度是64的异步时钟FIFO,因为FIFO读写位宽都是32bit,所以上游模块直接写入FIFO即可,这里和练习1中的方法完全一样,但是在读取FIFO的时候,又因为下游模块的读位宽是8bit,而一次性从FIFO中读出的数据是32bit,我们就需要用一个cnt计数器去计数拆分32bit的数据,dout再依次去输出从32bit数据拆分来的数据,同时也拉高dout_vld指示信号,如图1所示FIFO IP练习1的代码设计,具体细节笔者就不再赘述了。
对于FIFO IP练习1的Testbench,其实和FIFO读写位宽相同的设计也大同小异,先模拟上游模块向本模块的写入数据,再模拟输入下游模块准备就绪的rdy信号,这里只补充说明一点,因为FIFO写端口的输入时钟是50Mhz,而读端口的输出时钟是100Mhz,其中上游模块的写位宽din是32bit,下游模块的读位宽dout是8bit,所以给出120个时钟的rdy高电平,大家可以简单计算下,写端口属于clk_in时钟域,120个clk_in应该是120*20ns=2400ns。而读端口属于clk_out时钟域,2400ns就是对应写端口的2400ns/10ns=240个时钟周期,因为下游模块的读位宽是8bit,所以说要输出完32bit*60的数据,需要32bit*60/8bit也就是240个时钟周期,如图2是FIFO IP练习1的输入信号激励设计。
大家打开Vivado环境,添加好功能文件和测试文件后,启动Modelsim进行仿真,如图3是FIFO IP练习1的仿真结果,可以清楚地观察到当fifo_empty为高时,即FIFO当前已经没有数据了,此时恰好dout输出FIFO中的最后一个数据,且dout_vld被拉高,和我们预期的设计效果完全相符。
图1 FIFO IP练习1的代码设计
图2 FIFO IP练习1的输入信号激励设计
图3 FIFO IP练习1的仿真结果
练习2
设计一个模块包含读写位宽是32bit、读写深度是64的异步时钟FIFO,其中输入数据信号din和输入数据指示信号din_vld是属于clk_in时钟域的,上游模块会负责写数据到本模块的FIFO中,当本模块FIFO写端口已写入了60个数据,也就是FIFO快要写满溢出的时候,这时上游模块仍有数据要写入FIFO则直接丢弃该数据。下游模块负责从本模块的FIFO中读数据,当下游模块输入rdy信号时表示下游模块已准备好可以接收FIFO中的数据了,这时如果FIFO中有数据,那么就把FIFO中的数据赋值给输出数据信号dout送至下游模块并同时拉高dout_vld输出数据指示信号,其中输出数据信号dout和输出数据指示信号dout_vld则是属于clk_out时钟域的,上游模块din信号的写位宽是8bit,下游模块dout信号的读位宽是32bit,表2为练习2的信号列表。
信号列表 |
||
信号名 |
I/O |
位宽 |
clk_in |
I |
1 |
rst_n |
I |
1 |
rdy |
I |
1 |
din |
I |
8 |
din_vld |
I |
1 |
clk_out |
I |
1 |
dout |
O |
32 |
dout_vld |
O |
1 |
fifo_empty |
O |
1 |
表2 FIFO IP练习2设计中的信号列表
练习2和练习1一样都是在FIFO相同读写位宽的基础上的延伸扩展,当然Vivado环境下完全支持异步时钟FIFO配置成位宽不同的读写端口,实际工作中也有不少FPGA工程师习惯性去把异步时钟FIFO读写端口根据需求人为配置成位宽不同的,但是笔者还是推荐大家把读写位宽都配置成相同的,这样在程序设计上也更简便不需要再去考虑一些其他因素影响,这里练习1和练习2其实把现实工作中上游模块输入信号din和下游模块输出信号dout的两种可能情况都包括在内了,所以大家实践过这两个练习,在实际项目中完全可以灵活应用,就可以达到二次开发的效果,练习2是输入信号din位宽是32bit,输出信号dout位宽是8bit,所以我们需要对FIFO的输出进行拆分,而练习2相反的是输入信号din位宽是8bit,输出信号dout位宽是32bit,所以我们需要对FIFO的输入进行拼接,练习1和练习2中包含了对数据拼接和拆分的一般性方法,有很强的代表性,如图4所示FIFO IP练习2的代码设计。
对于FIFO IP练习2的Testbench,其实类似练习1,在练习2中因为FIFO写端口的输入时钟是50Mhz,读端口的输出时钟是100Mhz,这里上游模块的写位宽din是8bit,下游模块的读位宽dout是32bit,所以也给出了240个时钟周期的din_vld信号用以模拟上游模块向本模块写入240个8bit的数据,之后再去给出30个clk_in时钟周期的rdy高电平模拟下游模块读数据,这里30个clk_in是30*20ns=600ns,读端口在clk_out时钟域,600ns就对应读端口的600ns/10ns=60个时钟周期,因为下游模块的读位宽是32bit,所以说要输出完32bit*60的数据,需要60个时钟周期,如图5是FIFO IP练习2的输入信号激励设计。如图6 FIFO IP练习2的仿真结果,大家代入Modelsim下可以观察到和预期的设计效果完全一致。
图4 FIFO IP练习2的代码设计
图5 FIFO IP练习2的输入信号激励设计
图6 FIFO IP练习2的仿真结果
源工程代码下载链接:
链接:https://pan.baidu.com/s/1XF1unOQV_bYXAzbFoMstKQ
提取码:g2io
FPGA之FIFO详解,读写位宽不同相关推荐
- FPGA之FIFO详解,初识FIFO
FIFO IP介绍 在篇博客里引入FIFO IP核的概念,FIFO是FPGA中最常用的IP核,经常用在接口模块.串并转换.协议处理.数据缓存等很多场合,所以活学活用这个IP核对于后期项目 ...
- 位宽512bit显卡_显卡位宽是什么?详解显卡位宽基础知识科普!
由于买电脑的时候大家对显卡的显存大小过于重视,很多人忽视了显存位宽的重要性,甚至出现2GB独立显卡但是位宽只有64bit这样坑人的显卡.也许有人说,显卡位宽做大点不就好了么.这是不对的,显卡位宽的扩大 ...
- 解决FIFO读写位宽不等的问题
上周阿里面试官问ram两侧读写位宽不一样改如何解决?当时含糊了一下,事后再认真分析其中缘由. 思路 取读写位宽的最大公因数作为ram的位宽,控制读写指针的步进,并预测下一次的指针位置从而判断空满,和普 ...
- 读写位宽不同的FIFO,数据输入输出顺序是怎么样的?BRAM又如何呢?
原文地址:https://wenku.baidu.com/view/7d7cf156284ac850ac0242b6.html 对于BRAM: 1)写位宽小于读位宽: 先入存低位,后入存高位: 如写4 ...
- 面试——异步FIFO详解
1.异步FIFO简介及其原理 FIFO是英文First In First Out 的缩写,是一种先进先出的数据缓存器,它与普通存储器的区别是没有外部读写地址线,这样使用起来非常简单,但缺点就是只能顺序 ...
- iTextSharp 使用详解 读写PDF
iTextSharp 使用详解 PDF文件是目前比较流行的电子文档格式,在办公自动化(OA)等软件的开发中,经常要用到该格式,但介绍如何制作PDF格式文件的资料非常少,在网上搜来搜去,都转贴的是同一段 ...
- INF文件详解(32位64位兼容INF)
INF文件格式要求 一个INF文件是以段组织的简单的文本文件.一些段油系统定义(System-Defined)的名称,而另一些段由INF文件的编写者命名.每个段包含特定的条目和命名,这些命名用于引用I ...
- c语言比特和字节,详解 比特(位,bit),字节(Byte),字符的区别 *(转)
比特(位):英文bit,是计算机晶体管的一种状态(通电与断电).就是0与1,真与假,是计算机最基本的传输单位. 示例: 2bit : 10; 4bit : 1111; 8bit : 1111 1111 ...
- 位运算符Java与详解_java位运算符详解
java位运算符详讲 一.位运算符分类 java中位运算符主要有:按位与&.按位或|.按位非~.按位异或^. 在使用时,需要将运算数都转换为二进制再进行运算,若为负数则使用补码表示.二. ...
最新文章
- C# 全选中数字文本框内容
- java exec执行tar_用java调用rpmbuild 报错,同一条命令直接复制到终端却能运行
- php验证数字100倍数,js如何实现一个文本框只能输入数字 且是100的倍数
- 对一个简单汇编程序分析
- 弄懂goroutine调度原理
- Git的使用——解决中文乱码
- AndroidStudio_从Eclipse到AndroidStudio开发工具_两者使用的区别_通过向导新建项目和引入module---Android原生开发工作笔记68
- [转]java 输出流转输入流
- Centos6.5安装FastDFS
- 如何使用Spring Bean Configuration File调用构造方法并给参数赋值
- 干支纪年法VB编程:输入一个年份,程序会列出从该年份开始的12年的干支纪年和生肖,希望大神帮我解释期中的关键语句
- 区块链技术指南学习笔记1
- vi编辑器 末尾添加_linux下的VI编辑器使用手册
- Linux之IFS间隔符、C编程、gdb调试
- 我的 Input框 不可能这么可爱
- uniapp 图片缓存
- XXL-JOB研究二 调度中心
- i.MX6ULL终结者Linux I2C驱动实验IMX6ULL的I2C总线驱动分析
- 网站301跳转问题的探讨和用法,网站做301跳转的相关问题
- PostMan测试接口-----上传文件、导出excel