13hope:
个人理解,Verilog本身只是“建模”语言。具体到阻塞/非阻塞,只规定了两种赋值语句的行为。所以无论怎么写,仿真器和综合器都不会报错。但是存在两个问题,所描述的行为是否有物理电路与之对应;电路行为在仿真阶段和综合后是否一致。 像是电平敏感always快内使用多个多个非阻塞赋值就没有意义,仿真结果不可信
 
wjcdx:
> 个人理解,Verilog本身只是“建模”语言。
 
Verilog是个大杂烩(中性,非贬义),包含了支持验证、综合、测试的语法结构,比如:initial, repeat, forever, task等。
 
> 具体到阻塞/非阻塞,只规定了两种赋值语句的行为。所以无论怎么写,仿真器和综合器都不会报错。但是存在两个问题,所描述的行为是否有物理电路与之对应;电路行为在仿真阶段和综合后是否一致。
 
感谢提醒,可能就是与综合后电路一致的原因。Verilog发展历经了好多个版本,有可能是历史原因。
 
不过,最终要求的不是你建模的电路和综合后的电路一模一样,否则不是要写RTL代码,而是要画版图了。最终的要求是综合后的电路符合RTL描述的模型,行为一致。
 
RTL是一个抽象的建模层次,而不是物理的建模层次,无法与综合后的电路完全对应:比如+-x÷这些operators都不是使用电路描述的,但综合后却有电路,怎么对应呢?
 
还有综合器要对RTL的代码做优化,有一些电路不必要的会被优化掉,效率不高的会被优化成更高效的方式。
 
再有,很多时候使用的是工具提供的库里面的模块,这个是黑盒的,也不清楚里面的电路。
 
今天发现一个2001版本的新特性,可以佐证我的观点:
​​
 
从这个里面可以看到,register不是物理的寄存器(DFF)。而是一个变量数据类型(variable data type).
但是又遗留了明显针对物理寄存器的非阻塞赋值,做的不彻底。NBA增加了学习的难度,进而在使用中也会产生问题。
 
建模方法(Modeling Methodology)应该尽量简单,把这部分工作放在综合器里面去做更合适。能写综合器的人,都是对电路特性更了解的人,出错的概率更小。
 
RTL层建模需要的只是对变量赋值(variable assignment),甚至连 连续赋值 和 过程赋值 都不需要区分。这样的区分有助于理解,却不是必须。
 
> 像是电平敏感always快内使用多个多个非阻塞赋值就没有意义,仿真结果不可信
 
这个链接里有很多NBA在一个always块内:
https://github.com/alexforencich/verilog-ethernet/blob/master/rtl/arp_64.v
cache_query_request_ip_reg <= cache_query_request_ip_next;
outgoing_eth_dest_mac_reg <= outgoing_eth_dest_mac_next;
outgoing_arp_oper_reg <= outgoing_arp_oper_next;
outgoing_arp_tha_reg <= outgoing_arp_tha_next;
outgoing_arp_tpa_reg <= outgoing_arp_tpa_next;
wjcdx:
> 像是电平敏感always快内使用多个多个非阻塞赋值就没有意义,仿真结果不可信
昨天没看清楚,给的例子是边沿敏感。你说的是电平敏感。
 
其实,“电平敏感”这个词不准确,准确的说法是“电平变化敏感”:
always @(a, b, c)
begin
if (a) begin
end
end
 
这个并不是只在a为1时执行,在a为0时也执行。所以不是对a的高电平敏感,而是对a的电平变化敏感。
 
always在Verilog里面没有区分,在SystemVerilog里面区分的就比较细。上面的always在SystemVerilog里面应该是always_comb, 而不是always_seq,综合出来是组合电路,里面使用的是wire,而不是reg.
 
对wire使用非阻塞赋值是不正确的。这也是我为什么说在RTL建模时把NBA这个概念拿掉的原因:理解时容易混淆,使用时容易出错。
 
13hope:
很细致的回复,基本都赞同。只是最后一点,GitHub上的代码是always @(posedge clk)内部,用了多个<=赋值当然没问题,综合后就是一堆DFF。
 
至于我说的“没意义”,比如下面代码,a “电平变化敏感” (双沿),首先,想描述的一定是组合逻辑。其次,语义上非阻塞赋值是在当前仿真step之后同时给temp和b赋值,也就是说a值改变触发该always,其第二条在对temp采样时,temp还未更新,所以b始终等于a上一次“变化前”的值。这个“行为”没有任何组合电路与之对应(组合电路没有记忆功能)。
always @(a) begin
temp <= a;
b <= temp;
end
 
至于综合后,b确实是一根wire直接连到a,temp可能被优化掉,但仿真结果与综合不一致。
Verilog非常容易写出仿真与综合行为不一致的电路,所以有很多guideline帮助构建可综合电路。
 
 
wjcdx:
如果不存在NBA,可能就不会存在这样的问题了。
如果不存在NBA,则continuous和procedural assignment都只是简单的使用等号“=”来表示。
 
1.
always @(a) begin
temp = a;
b = temp;
end
 
这样的写法意思是,如果a变化,则把a的值赋值给temp, 然后在把temp的值赋值给b。
这是简单的组合逻辑,可以化简为:
assign b = a;
 
 
2. 如果想让b每次都取a上一次的值,则可以写成:
always @(a) begin
b = temp;
temp = a;
end
 
仿真和综合针对这个写法,不清楚是否一致?
 
仿真器想必不会出错,综合器如何决定这两条赋值语句能否调换顺序呢?要做数据流分析。
如果两条赋值语句各自的left hand side与对方的right hand side存在关联,或者反过来存在关联的话,就说明存在顺序关系。如果没有,则不存在顺序关系,两条赋值语句可以分开综合。
 
综合器把这个事情做了以后,就可以把建模人员解放出来,只关心值的传递这个核心问题即可,
而不用考虑仿真时值如何赋值,综合后电路如何赋值,这样的问题。
 
建模人员保证值传递的逻辑时正确的。仿真器保证仿真的正确性,综合器保证综合出的电路符合模型要求的值传递逻辑。
各司其职,正确的人做正确的事,专业的人做各自专业领域的事,这样可以减少出错。
 
当然,建模人员了解仿真器和综合器的工作原理是有益的。
 
回到这个例子上来,如果建模人员考虑的是变量之间的值如何传递,
而不是仿真时什么时候采样,什么时候赋值,出错的可能性就小多了。

非阻塞赋值(Non-blocking Assignment)是个伪需求(2)的更多相关文章

  1. 非阻塞赋值(Non-blocking Assignment)是个伪需求

    https://mp.weixin.qq.com/s/mH84421WDGRb7cuU5FEFIQ Verilog的赋值很是复杂,包括: 1. Continuous assignment; 2. Pr ...

  2. 【Verilog HDL】赋值语句之阻塞赋值方式与非阻塞赋值方式

    刚开始接触Verilog HDL语言时,这种硬件描述语言有一点与软件的程序设计语言直观上的最大区别大概就是这个赋值语句了(这里只是强调直观上的最大区别,事实上的最大区别并非如此). Verilog H ...

  3. FPGA之阻塞赋值与非阻塞赋值

    Verilog语言中讲的阻塞赋值与非阻塞赋值,但从字面意思来看,阻塞就是执行的时候在某个地方卡住了,等这个操作执行完在继续执行下面的语句,而非阻塞就是不管执行完没有,我不管执行的结果是什么,反正我继续 ...

  4. Verilog之阻塞赋值非阻塞赋值

    verilog设计进阶 时间:2014年5月6日星期二 主要收获: 1. 阻塞赋值与非阻塞赋值: 2. 代码测试: 3. 组合逻辑电路和时序逻辑电路. 阻塞赋值与非阻塞赋值: 1. 阻塞赋值" ...

  5. 07-阻塞赋值与非阻塞赋值原理分析——小梅哥FPGA设计思想与验证方法视频教程配套文档

    芯航线--普利斯队长精心奉献   实验目的:掌握阻塞赋值与非阻塞赋值的区别 实验平台:无 实验原理:     阻塞赋值,操作符为"=","阻塞"是指在进程语句( ...

  6. 阻塞赋值与非阻塞赋值(verilog篇)

    阻塞赋值与非阻塞赋值(verilog篇) 2017-09-30 竹海 相约电子ee 相信刚刚接触verilog的读者,多少对阻塞赋值和非阻塞赋值仍有一些困惑.笔者在这篇文章,带领大家深入的理解这两者的 ...

  7. 阻塞赋值-非阻塞赋值(LUT,FDC,BUF...)

    一.看RTL级综合网络 1.1 FDC FDPE FDRE FDSE均是XILINX FPGA片上资源中四种不同的触发器,具体功能可直接百度 1.2 LUT是实现组合逻辑功能的一张真值表,根据输入值直 ...

  8. stm32中阻塞模式和非阻塞模式 in blocking mode 与 in non-blocking mode区别

    阻塞模式和非阻塞模式...... 我的理解是:阻塞模式就像是一个延时函数,当这个函数没处理完那么,所有的按照流程需要执行的代码都不会被执行,要等到这个延时完成,类似 平时看书上写的LED灯闪烁,用的d ...

  9. verilog阻塞与非阻塞的初步理解(二)

    将阻塞模块改为下述代码: module blocking(clk,a,b,c); :] a; input clk; :] b,c; :] b,c; always @(posedge clk) begi ...

随机推荐

  1. Spring Cloud 学习 之 Spring Cloud Eureka(概述)

    Spring Boot版本:2.1.4.RELEASE Spring Cloud版本:Greenwich.SR1 前述: ​ 服务治理可以说是微服务架构中最为核心和基础的模块,它主要用来实现各个微服务 ...

  2. vue-cli3使用全局scss

    在开发项目的时候,经常会出现多个元素样式相同,比如颜色相同.这里就需要我们设置公共样式,方便后期调试 一配置方法 1.在src/assets/styles目录下创建文件variable.scss // ...

  3. centos7启动httpd服务失败:Job for httpd.service failed because the control process exited with error code.

    centos7启动httpd命令有两个可以用 service httpd start    systemctl start httpd.service 如果出现如下报错 Job for httpd.s ...

  4. 使用 pyautogui 进行跨平台的 GUI 自动化操作

    有个朋友最近问我有没有推荐 GUI 桌面应用自动化的技术,我只能回答他:不好意思,这个真有,他是 pyautogui.主要有三大特征: 纯纯的 python, 源码一览无余: 跨平台,linux, w ...

  5. 在没有RedirectAttributes的环境中如何在重定向环境中报错错误提示信息供页面使用

    Spring在无RedirectAttributes的情况下(如Interceptor.filter中)使用Flash scope 今天遇到一个应用场景: 在需要在自定义的Interceptor中判断 ...

  6. linux --vim 补充 .vimrc

    1.今天发现了一个新的功能.vimrc 1.这个是一个个人配置文件,可以在这个里面首先对vim进行一些设置呢 如果系统没有.vimrc文件,可以自己创建一个,touch .vimrc 举个栗子,我在. ...

  7. angular 实现依赖注入

    1:首先获取module对象var myAppModule = angular.module('myApp', []); 2:定义对象(类似spring中xml声明bean对象<bean id= ...

  8. 我的linux学习日记day8

    链接文件 linux中链接有两种,一种是硬链接,一种是软链接 一.硬链接 硬链接是指通过索引节点来进行链接创建硬链接的方法如下:ln 源文件 硬链接文件具有相同inode号的多个文件互为硬链接文件删除 ...

  9. ES6-10笔记(二)

    class类 Javascript是一种基于对象(object-based)的语言,你遇到的所有东西几乎都是对象.但是,它又不是一种真正的面向对象编程(OOP)语言,因为它的语法中没有class(类) ...

  10. kafka如何防止key相同的消息并发消费

    最开始,我认为只用把消费者设置为单线程消费,就可以避免并发问题. 因为同一个key,分区一定相同,那么就只会被同一个消费者消费,消费者又是单线程,这样就避免了并发问题 后面发现,上述的方式没有办法处理 ...