2956|1

6892

帖子

0

TA的资源

五彩晶圆(高级)

楼主
 

Verilog 阻塞/非阻塞用法 基础 [复制链接]

两个要点:

×在描述组合逻辑的always块中用阻塞赋值,则综合成组合逻辑的电路结构。
×在描述时序逻辑的always块中用非阻塞赋值,则综合成时序逻辑的电路结构。

为了更好地理解上述要点,我们需要对Verilog 语言中的阻塞赋值和非阻塞赋值的功能和执行时间上的差别有深入的了解。为了解释问题方便下面定义两个缩写字:
RHS – 方程式右手方向的表达式或变量可分别缩写为: RHS表达式或RHS变量。 LHS – 方程式左手方向的表达式或变量可分别缩写为: LHS表达式或LHS变量。 
IEEE Verilog标准定义了有些语句有确定的执行时间,有些语句没有确定的执行时间。若有两条或两条以上语句准备在同一时刻执行,但由于语句的排列次序不同(而这种排列次序的不同是IEEE Verilog标准所允许的), 却产生了不同的输出结果。这就是造成Verilog模块冒险和竞争现象的原因。为了避免产生竞争,理解阻塞和非阻塞赋值在执行时间上的差别是至关重要的。

阻塞赋值
 
阻塞赋值操作符用等号(即 = )表示。为什么称这种赋值为阻塞赋值呢?这是因为在赋值时先计算等号右手方向(RHS)部分的值,这时赋值语句不允许任何别的Verilog语句的干扰,直到现行的赋值完成时刻,即把RHS赋值给 LHS的时刻,它才允许别的赋值语句的执行。一般可综合的阻塞赋值操作在RHS不能设定有延迟,(即使是零延迟也不允许)。从理论上讲,它与后面的赋值语句只有概念上的先后,而无实质上的延迟。 若在RHS 加上延迟,则在延迟期间会阻止赋值语句的执行, 延迟后才执行赋值,这种赋值语句是不可综合的,在需要综合的模块设计中不可使用这种风格的代码。
  
阻塞赋值的执行可以认为是只有一个步骤的操作:

计算RHS并更新LHS,此时不能允许有来自任何其他Verilog语句的干扰。 所谓阻塞的概念是指在同一个always块中,其后面的赋值语句从概念上(即使不设定延迟)是在前一句赋值语句结束后再开始赋值的。

如果在一个过程块中阻塞赋值的RHS变量正好是另一个过程块中阻塞赋值的LHS变量,这两个过程块又用同一个时钟沿触发,这时阻塞赋值操作会出现问题,即如果阻塞赋值的次序安排不好,就会出现竞争。若这两个阻塞赋值操作用同一个时钟沿触发,则执行的次序是无法确定的。下面的例子可以说明这个问题。

[例1]. 用阻塞赋值的反馈振荡器
    module fbosc1 (y1, y2, clk, rst);
      output y1, y2;
      input  clk, rst;
      reg    y1, y2;

      always @(posedge clk or posedge rst)
        if (rst) y1 = 0;  // reset
        else     y1 = y2;

      always @(posedge clk or posedge rst)
        if (rst) y2 = 1;  // preset
        else     y2 = y1;
    endmodule
    
按照IEEE Verilog 的标准,上例中两个always块是并行执行的,与前后次序无关。如果前一个always块的复位信号先到0时刻,则y1 和y2都会取1,而如果后一个always块的复位信号先到0时刻,则y1 和y2都会取0。这清楚地说明这个Verilog模块是不稳定的会产生冒险和竞争的情况。

非阻塞赋值

非阻塞赋值操作符用小于等于号 (即 <= )表示。为什么称这种赋值为非阻塞赋值?这是因为在赋值操作时刻开始时计算非阻塞赋值符的RHS表达式,赋值操作时刻结束时更新LHS。在计算非阻塞赋值的RHS表达式和更新LHS期间,其他的Verilog语句,包括其他的Verilog非阻塞赋值语句都能同时计算RHS表达式和更新LHS。非阻塞赋值允许其他的Verilog语句同时进行操作。非阻塞赋值的操作可以看作为两个步骤的过程:

1)    在赋值时刻开始时,计算非阻塞赋值RHS表达式。
2)    在赋值时刻结束时,更新非阻塞赋值LHS表达式。

非阻塞赋值操作只能用于对寄存器类型变量进行赋值,因此只能用在"initial"块和"always"块等过程块中。非阻塞赋值不允许用于连续赋值。下面的例子可以说明这个问题:

[例2]. 用非阻塞赋值的反馈振荡器
    module fbosc2 (y1, y2, clk, rst);
      output y1, y2;
      input  clk, rst;
      reg    y1, y2;

      always @(posedge clk or posedge rst)
        if (rst) y1 <= 0;  // reset
        else     y1 <= y2;

      always @(posedge clk or posedge rst)
        if (rst) y2 <= 1;  // preset
        else     y2 <= y1;
    endmodule

同样,按照IEEE Verilog 的标准,上例中两个always块是并行执行的,与前后次序无关。无论哪一个always块的复位信号先到, 两个always块中的非阻塞赋值都在赋值开始时刻计算RHS表达式,,而在结束时刻才更新LHS表达式。所以这两个always块在复位信号到来后,在always块结束时 y1为0而y2为1是确定的。从用户的角度看这两个非阻塞赋值正好是并行执行的。 
---------------------------------------------------------------------------
掌握可综合风格的Verilog模块编程的八个原则会有很大的帮助。在编写时牢记这八个要点可以为绝大多数的Verilog用户解决在综合后仿真中出现的90-100% 的冒险竞争问题。
1)    时序电路建模时,用非阻塞赋值。
2)    锁存器电路建模时,用非阻塞赋值。
3)    用always块建立组合逻辑模型时,用阻塞赋值。
4)    在同一个always块中建立时序和组合逻辑电路时,用非阻塞赋值。
5)    在同一个always块中不要既用非阻塞赋值又用阻塞赋值。
6)    不要在一个以上的always块中为同一个变量赋值。
7)    用$strobe系统任务来显示用非阻塞赋值的变量值
8)    在赋值时不要使用 #0 延迟

此帖出自FPGA/CPLD论坛

最新回复

yo还有点像夏老师的书里的嘛  详情 回复 发表于 2012-2-21 09:13
点赞 关注
 

回复
举报

7219

帖子

192

TA的资源

五彩晶圆(高级)

沙发
 
yo还有点像夏老师的书里的嘛
此帖出自FPGA/CPLD论坛
 
 

回复
您需要登录后才可以回帖 登录 | 注册

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/9 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2025 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表