首先引入一个例子:

`timescale  1ns/100ps

module   TB;                                                                                       module  INV_DFF(Clock, Reset_n, DataIn, DataOut);

reg Ck, Rst_n, Din;                                                                                  input Clock;

wire Dout;                                                                                               input Reset_n;

//Clock  generation                                                                                  input DataIn;

initial   begin                                                                                           output reg Data_Out

Ck = 0;                                                                                   wire DataInv;

forever   #10 Ck = ~Ck;                                                           always @(posedge Clock or negedge Reset_n)

end                                                                                                           begin if(~Reset_n)

//Reset  generation                                                                                                            Data_Out <= 1'b0;

initial   begin                                                                                                                  else Data_Out <= Data_Inv;

Rst_n = 1;                                                                                             end

#5 Rst_n = 0;                                                                          assign #3 DataInv = ~ DataIn;

#55 Rst = 1;                                                                        endmodule

end

//Data input generation

initial   begin

Din = 0;

#80 Din = 1;

#40 Din = 0;

end

INV_DFF     u_INV_DFF(                 //DUV

.Clock(Ck),

.Reset_n(Rst_n),

.DataIn(Din),

.DataOut(Dout),

);

0仿真时刻:3个initial进程和1个DUV同时执行。同时执行的进程其顺序不是固定的,和所用的仿真器有关,假设此处的同时执行,按代码中的顺序来执行。

执行Clock Generation 中的语句Ck = 0; ~Ck。 执行forever #10 进程挂起。

执行Reset Generation 中的语句Rst_n = 1; #5 进程挂起。

执行Data Input Generation中的语句Din = 0; #80 进程挂起。

执行DUV中的语句~DataIn; #3进程挂起。always @进程挂起。 至此0仿真时刻的语句全部执行完毕,仿真时间轴向前推进。

3仿真时刻:只有一个计算事件 DataInv = #3 ~DataIn;更新DataInv的值。无触发更多计算事件,所以仿真时间轴向前推进。

5仿真时刻:执行Reset Generation 中的语句 Rst_n = 0; #55 进程挂起。

由于Rst_n的更新时间,DUV中的always @进程执行,DataOut值更新。无触发更多计算事件,仿真时间轴向前推进。

10仿真时刻: 执行Clock Gneration 中的计算事件CK。更新事件触发。#10进程挂起。

执行DUV中的always进程,计算事件Data_Out = 0。无触发更多事件,仿真时间轴向前推进。

60仿真时刻: 执行Clock Gneration 中的计算事件CK。更新事件触发。#10进程挂起。

执行Reset Generation 中的语句 Rst_n = 1; 进程结束。

执行DUV中的always进程,计算事件Data_Out = 1(Rst_n的值已经为1)。无触发更多事件,仿真时间轴向前推进。

80仿真时刻: 执行Clock Gneration 中的计算事件CK。更新事件触发。#10进程挂起。

执行Data Input Generation中的语句Din = 1; #40 进程挂起。

执行DUV中的always进程,计算事件Data_Out = Data_Inv。

执行DUV中的语句~DataIn; #3进程挂起。always @进程挂起。 至此0仿真时刻的语句全部执行完毕,仿真时间轴向前推进。

仿真时间:是仿真时间维护的时间值,用来对仿真电路的真实时间进行建模(仿真时间和软件的执行时间没有任何联系),当仿真时间推进到某一个时间点时,该时间点就被称为当前仿真时间,而以后的任何时间都被称为将来仿真时间。

事件:模型中数值的变化,功能仿真是一种事件驱动的仿真,整个仿真过程都是围绕事件来组织的。

更新事件:在被仿真的电路中,线网或寄存器的值在任何进程中的任何改变都被认为是一个更新事件。

计算事件:由于更新事件产生的,进程的计算,计算事件。

计算事件和更新事件之间循环往复的互相触发,推动仿真时间的前进。

进程是Verilog中的独立执行单元,包括:原语(Primitives), 模块(Moules), initial过程块, always过程块, 连续赋值语句(assign), 异步任务(task)。在仿真时,所有的进程都是仿真器按Verilog的语义来顺序执行的,效果是各个进程并行执行的效果,在未执行完当前所有的进程时,仿真时间不会向前推进。

initial   begin

Ck = 0;  forever Ck = ~Ck;

end

例子会hang在仿真时刻0,因为更新时间一直触发计算事件,计算事件一直触发更新时间。

Verilog中的时序控制:事件语句(@),延时语句(#),等待语句(wait)。

Verilog仿真时的不确定性:在同一个仿真时间内,几个同一调度模块中事件执行顺序的任意性,进程之间语句的任意交织。

verilog或者systemverilog相对于C,能用于硬件建模的最大区别:

1)connectivity  一个大的design可以由很多block,组成,通过例化或者interface来进行连接

2)time   time的变化可以使得design的state变化,与执行时间(execution time)完全不同,通过@/wait/#来实现

3)concurrency    event之间的同步发生关系, 通过initial/always/fork join来实现

对于验证还缺少:1)randomization;  2)constrainability;  3)functional coverage;

在simulator中的concurrency是基于time_share的来跑的,CPU轮询执行。

always模块,initial模块,连续赋值模块,fork/join,都是完全并行执行的,并没有先后顺序。

在基于time-sharing的处理中,simulator对于各个并行thread,保证访问机会时一样的,但是各个模块的先后顺序不能保证,

和代码块中的位置有关。simulator也不会自己关掉一个thread,除非自己执行结束。

Verilog的事件调度:

在systemverilog中有两种thread,module thread和program thread,module thread主要用来建模design,

program thread主要用来建模testbench。

program中的task的执行,主要看task的定义位置,如果是在module内定义的task,则尽管在program中调用,也算是一个

module thread。

对于program和module内的class的执行顺序,systemverilog标准中,并没有准确给出,根据simulator的实现而不同。

program中在SV2012中,才开始支持非阻塞赋值。

其中的执行顺序:

1)sample阶段,进行clock,property这样的采样。

2)excute阶段,执行阻塞赋值等。

3)reactive阶段,执行非阻塞赋值等。以及阻塞赋值的迭代。

4)evaluate阶段,执行assertion的判断。

5)program thread阶段,执行program中的阻塞赋值,非阻塞赋值

simulation的前进,依靠两条线,一条simulation time,另一个是module thread中的非阻塞赋值和阻塞赋值之间的迭代。

其中第二种也称为delta cycle,一个设计中可能会有很多delta cycle,因为信号的依赖关系可以一直迭代。

几种存在race condition的情况:

1)concurrent中的冲突:

2)delta cycle对clock的影响:

如果两个时钟有信号之间的采样关系,而且一个clock比另一个clock多一个非阻塞赋值。

此时,两个clock之间会差一个delta cycle,在RTL仿真时,两个clock之间的信号采样会出错。

快一点的clock的值,可以再被慢一点的采到,但是在波形中不会体现出来。

这时的解决方法:

1)手工增加delay

2)将另一个clock 也经过一个非阻塞赋值。

Verilog篇(三)仿真原理的更多相关文章

  1. VCS使用学习笔记(1)——Verilog相关的仿真知识

    本文主要学习Verilog的仿真特性,以及仿真器对Verilog的处理,算是对Verilog知识的增量学习.本文内容与我的另一篇博文(http://www.cnblogs.com/IClearner/ ...

  2. 敌情篇 ——DDoS攻击原理

    敌情篇 ——DDoS攻击原理 DDoS攻击基础 DDoS(Distributed Denial of Service,分布式拒绝服务)攻击的主要目的是让指定目标无法提供正常服务,甚至从互联网上消失,是 ...

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

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

  4. 【基于WinForm+Access局域网共享数据库的项目总结】之篇三:Access远程连接数据库和窗体打包部署

    篇一:WinForm开发总体概述与技术实现 篇二:WinForm开发扇形图统计和Excel数据导出 篇三:Access远程连接数据库和窗体打包部署 [小记]:最近基于WinForm+Access数据库 ...

  5. 【基于WPF+OneNote+Oracle的中文图片识别系统阶段总结】之篇三:批量处理后的txt文件入库处理

    篇一:WPF常用知识以及本项目设计总结:http://www.cnblogs.com/baiboy/p/wpf.html 篇二:基于OneNote难点突破和批量识别:http://www.cnblog ...

  6. 【SSRS】入门篇(三) -- 为报表定义数据集

    原文:[SSRS]入门篇(三) -- 为报表定义数据集 通过前两篇文件 [SSRS]入门篇(一) -- 创建SSRS项目 和 [SSRS]入门篇(二) -- 建立数据源 后, 我们建立了一个SSRS项 ...

  7. 机器学习之决策树三-CART原理与代码实现

    决策树系列三—CART原理与代码实现 本文系作者原创,转载请注明出处:https://www.cnblogs.com/further-further-further/p/9482885.html ID ...

  8. 爬虫前篇 /https协议原理剖析

    爬虫前篇 /https协议原理剖析 目录 爬虫前篇 /https协议原理剖析 1. http协议是不安全的 2. 使用对称秘钥进行数据加密 3. 动态对称秘钥和非对称秘钥 4. CA证书的应用 5. ...

  9. Verilog学习笔记设计和验证篇(三)...............同步有限状态机的指导原则

    因为大多数的FPGA内部的触发器数目相当多,又加上独热码状态机(one hot code machine)的译码逻辑最为简单,所以在FPGA实现状态机时,往往采用独热码状态机(即每个状态只有一个寄存器 ...

随机推荐

  1. php 加密压缩

    php 把文件打成压缩包 ,可以去搜下 pclzip 搜很好多地方没有找到对压缩包进行加密操作的. 如果服务器是linux 那么见代码: $filename="test.csv"; ...

  2. javaagent

    -javaagent:<jarpath>[=<options>]load Java programming language agent, see java.lang.inst ...

  3. Unity3D笔记十三 摄像机之间切换

    using UnityEngine; using System.Collections; public class _5_6 : MonoBehaviour { private GameObject ...

  4. centos 6.6编译安装nginx

    nginx 安装 安装前必要软件准备 1)安装pcre.gzip 等为了支持rewrite功能,我们需要安装pcre # yum install -y pcre* zlib zlib-devel op ...

  5. where are you from

    where are you from 如果问美国人这句话的话,他们一般会说: I'm from California. I'm from Pennsylvanian. 一般是说州,而不是说Americ ...

  6. VS2015 中使用 MVC4

    最近把机子升级到win10 觉得还是好用, 又看了一个vs最新版,于时就安了个vs2015 可以前MVC4的项目用不起了 System.Web.Mvc这个有叹号,生成还要报错, 看了一下原因找不到4. ...

  7. 开放思源 专注高效 HPE&msup软件技术开放日回顾

    7月22日,HPE和msup联合举办的软件技术开放日在上海浦东新区张江高科技园区召开,主.分会场共邀请HPE 13 名测试.质量.大数据专家分享技术实践与经验,与180多名测试总监一起拆解质量保障及大 ...

  8. 2013Top100summit公布重量级演讲嘉宾及大会日程

    TOP100SUMMIT对外公布重量级嘉宾及大会日程 第四届技术商业论坛暨全球软件案例研究峰会(TOP100summit)将于11月23-26日北京召开.本届大会以“技术推动商业变革”为主题,力邀业界 ...

  9. ubuntu16.04下安装kdevelop和汉化

    1.Kdevelop安装 最简单的命令行安装,打开终端,执行 sudo apt-get install kdevelop 2.Kdevelop汉化 不需要自己下载汉化包,Kdevelop安装后,在终端 ...

  10. MapReduce部分源码解读(一)

    /** * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agree ...