在我看过的很多代码中,发现许多人在对变量赋初始值(或常量值)0时的做法各种各样,现在来分析下这几种情况对设计的影响。以对64位变量a赋初始值0为例:
(1)第一种:a <= 64’d0; 对于这种指定变量具体位宽的代码风格,我是直接否定的,因为它不利于参数化设计;
(2)第二种:a <= 0;(或a <= (0);)而对于这种直接赋一个0的做法呢,一般情况下对设计是没有影响的,而且还能进行参数化设计,但是在另外一种情况下是要注意的,就是例化子模块时对位宽大于32的变量赋0,就会出现意想不到的情况。现在举个简单的例子来证实这种情况。假设在子模块中对一个64位的输入变量取反后进行输出,而在顶层模块中将子模块输出变量的第33位进行输出,用于硬件led的测试。
顶层模块:
/**********************************版权申明************************************
**---------------------------------文件信息---------------------------------------------
** 文件名: led_top.v
** 创建者: CrazyBird
** 创建日期: 2015-8-2
** 版本号: v1.0
** 功能描述: 对变量直接赋0的测试
**
****************************************************************************/
// synopsys translate_off
`timescale 1 ns / 1 ps
// synopsys translate_on
module led_top(
led_data
);
//*************************************************************************
// 输入/输出端口定义
//*************************************************************************
output led_data;
//*************************************************************************
// 变量定义
//*************************************************************************
wire [63:0] dout;
//*************************************************************************
// 模块例化
//*************************************************************************
led u_led(
.din(0),
.dout(dout)
);
assign led_data = dout[32];
//*************************************************************************
endmodule
//********************************文件结束*************************************
子模块:
/*********************************版权申明************************************
**-------------------------------------文件信息-----------------------------------------
** 文件名: led.v
** 创建者: CrazyBird
** 创建日期: 2015-8-2
** 版本号: v1.0
** 功能描述: 对64位的输入数据取反后输出
**
***************************************************************************/
// synopsys translate_off
`timescale 1 ns / 1 ps
// synopsys translate_on
module led(
din,
dout
);
//************************************************************************
// 输入/输出端口定义
//************************************************************************
input [63:0] din;
output [63:0] dout;
//************************************************************************
// 取反输出
//************************************************************************
assign dout = ~din;
//************************************************************************
endmodule
//*******************************文件结束*************************************
modelsim仿真结果:
很显然,在例化子模块时对位宽大于32的变量赋0时其实只对低32位赋了0值。
那么这样的代码风格对设计实现有没有影响呢?接着对设计进行综合后出现以下警告(也提示只对低32位赋了值):
最后对设计进行分配引脚、实现以及生成bit文件并将bit文件下载到红色飓风开发板上验证一下,发现led亮了(高电平点亮的),呵呵,一个不定值居然让led亮了,我不知道硬件是怎么实现的。
(3)第三种:a <= {(DATA_WIDTH){1’b0}}; 其中DATA_WIDTH是经过定义的参数:parameter DATA_WIDTH = 64;对于第三种代码风格我是极力推荐的,因为它既实现参数化设计,又不会出现第二种代码风格的情况,具体呢,大家可以亲自验证下,哈哈!