本文转载自:<span id="profileBt"><a href="https://blog.csdn.net/wuyanbei24/article/details/104857004">搞FPGA开发的Ton…;
<font color="#FF8000">注:本文由作者授权转发,如需转载请联系作者本人</font>
<strong>FPGA Base 生成块</strong>
在FPGA编码的时候,如果多使用生成块语句,敲代码的时间大大减少。但是,代码的可读性会更高。自己平时在编写Verilog代码时,其实对这块语法并不是那么熟悉,所以这里专门整理一下,一来加深自己的记忆,二来方便自己以后查询。
<strong>生成块</strong>
动态的生成Verilog代码,方便参数化模块的生成。适用场景:
<li>对向量中的多个位进行重复操作</li>
<li>多个模块的实例引用</li>
<li>根据参数定义来确定陈序中是否应该包含某段Verilog代码</li>
编写代码是必须在模块中说明生成实例的范围,关键字generate—endgenerate用来指定该范围。生成的内容:
<strong>模块</strong>
<li>用户自定义原语</li>
<li>门级原语</li>
<li>连续赋值语句</li>
<li>initial和always块</li>
创建生成语句的三种方式:
<li>循环生成</li>
<li>条件生成</li>
<li>case生成</li>
<strong>循环生成</strong>
localparam N = 16;
genvar j;
generate for(j=0; j<N; j=j+1) being
// 需要循环生成的内容
// 变量声明
//模块
//用户自定义原语、门级原语
//连续赋值语句
//initial、always块
end
endgenerate
<strong>条件生成语句</strong>
类似于if-else-if的生成结构,该生成结构可以在设计模块中依据经过仔细推敲后编写的表达式值的真假,决定是否调调用。
parameter AD_DW = 16;
generate
if(AD_DW = 8)
// 需要循环生成的内容
//模块
//用户自定义原语、门级原语
//连续赋值语句
//initial、always块
else
endgenerate
<strong>case 生成语句</strong>
在设计模块中,经过仔细推敲确定多选一case结构,有条件地调用
parameter N = 8;
generate
case(N)
// 需要循环生成的内容
//模块
//用户自定义原语、门级原语
//连续赋值语句
//initial、always块
endcase
endgenerate
<strong>总结</strong>
在做图像处理的时候,经常会用到以上内容,以一个5*5的卷积运算为例:
<li>FPGA中不考虑面积,同时调用25个乘法器</li>
<li>同时定义6个BRAM用于实现行缓存</li>
如果采用循环生成的方式,这样代码的长度会大幅度的减少,同时代码可读性也会提高,自然代码的维护难度也会降低。
同时在调试的时候,根据条件生成语句,能快速屏蔽掉一些模块,这样调试工程占用的FPGA资源较少,在implement阶段会加快速度,加快调试进度。相比于整段的注释掉,通过修改一个parameter也会减少在注释时引入的编辑错误。