📅  最后修改于: 2021-01-11 14:36:13             🧑  作者: Mango
在Verilog中,行为模型包含过程语句,该过程语句控制模拟并操纵数据类型的变量。
这些声明包含在过程中。每个过程都有一个与之关联的活动流。
在行为模型仿真期间,由always和initial语句定义的所有流程在仿真时间零开始一起开始。
初始语句执行一次,而always语句则重复执行。
例
在模拟时间零,寄存器变量a和b分别初始化为二进制1和0。
初始语句已完成,并且在该模拟运行期间不再执行。此初始语句包含一个语句的开始-结束块。在该开始端型块,首先被初始化,随后用b。
module behave;
reg [1:0]a,b;
initial
begin
a = 'b1;
b = 'b0;
end
always
begin
#50 a = ~a;
end
always
begin
#100 b = ~b;
end
End module
过程分配用于更新整数,reg,时间和内存变量。过程分配和连续分配之间存在显着差异,例如:
1.每当输入操作数更改值时,连续赋值就会驱动净变量,求值并进行更新。
程序分配在围绕它们的程序流程构造的控制下更新寄存器变量的值。
2.过程分配的右侧可以是任何求值的表达式。但是,右侧的零件选择必须具有恒定的索引。左侧表示从右侧接收分配的变量。过程分配的左侧可以采用以下形式之一:
在延迟分配中,在执行语句之前经过了Δt个时间单位,并进行了左侧分配。由于存在内部分配延迟,因此会立即评估右侧,但是在将结果放入左侧分配之前会有Δt延迟。
如果另一个过程在Δt期间改变了右侧信号,则不会影响输出。综合工具不支持延迟。
句法
分配具有以下语法,例如:
Procedural Assignmentvariable = expression
Delayed assignment#Δt variable = expression;
Intra-assignment delayvariable = #Δt expression;
必须先执行阻塞过程分配语句,然后才能在顺序块中执行紧随其后的语句。
该语句不会阻止在并行块中执行其后的语句。
句法
以下语法适用于阻塞过程分配,例如:
=
非阻塞过程分配用于调度分配而不会阻塞过程流。
每当我们想要在同一时间步内进行多个寄存器分配而无需考虑顺序或彼此依赖时,都可以使用非阻塞过程语句。
句法
以下语法适用于非阻塞过程分配:
<=
当模拟器遇到非阻塞过程分配时,模拟器将分两步评估并执行非阻塞过程分配:
步骤1:模拟器评估右侧,并在过程定时控件指定的时间安排新值的分配。
步骤2:在时间步骤的末尾,当给定的延迟已到期或发生了适当的事件时,模拟器通过将值分配给左侧来执行分配。
条件语句或if-else语句用于决定是否执行一条语句。
句法
语法如下:
::= if ( )
||= if ( )
else
::=
||= ;
case语句是唯一的多向决策语句,用于测试一个表达式是否与其他几个表达式匹配,并相应地进行分支。
case语句对于描述例如微处理器指令的解码很有用。
句法
case语句具有以下语法:
::= case ( ) + endcase
||= casez ( ) + endcase
||= casex ( ) + endcase
::= <,>* :
||= default :
||= default
case语句与多路if-else-if构造在两个基本方面不同,例如:
1. if-else-if构造中的条件表达式比case语句中的一个表达式与其他多个表达式相比更通用。
2.当表达式中有x和z值时,case语句提供确定的结果。
循环语句有四种类型。它们用于控制零次,一次或多次语句的执行。
1.永远持续执行一条语句。
2.重复执行一条语句固定次数。
3.在执行语句直到表达式变为假之前,如果表达式开始为假,则根本不执行该语句。
4.对于控件,通过三个步骤执行其关联语句:
步骤1:执行通常用于初始化变量的赋值,该变量控制执行的循环数。
步骤2:评估表达式。假设结果为零,则for循环退出。如果它不为零,则for循环执行其关联的语句,然后执行步骤3。
步骤3:执行通常用于修改循环控制变量值的赋值,然后重复步骤2。
句法
以下是循环语句的语法规则,例如:
::= forever
||=forever
begin
+
end
::= repeat ( )
||=repeat ( )
begin
+
end
::= while ( )
||=while ( )
begin
+
end
::= for ( ; ; )
||=for ( ; ; )
begin
+
end
Verilog通过以下方式处理延迟控制,例如:
1.延迟控制
可以使用以下语法来延迟控制过程语句的执行:
::=
::= #
||= #
||= # ( )
以下示例将分配的执行延迟了10倍。
#10 rega = regb;
通过表达式的值指定的仿真时间来执行分配延迟。
2.事件控制
通过使用以下事件控制语法,可以将过程语句的执行与网络或寄存器上的值更改或声明的事件的发生同步:
::=
::= @
||= @ ( )
::=
||= posedge
||= negedge
||= >
*
网络和寄存器上的值更改可以用作触发语句执行的事件。这称为检测隐式事件。
Verilog语法还用于根据更改的方向来检测更改,该更改的方向是朝向值1(冒口)或朝向值0(负)。
对于未知表达式值,posege和negedge的行为是:
在以下四个模块之一中指定了Verilog中的所有过程。
初始块
在模拟开始时会启用initial和always语句。初始块仅执行一次,并且语句结束后其活动终止。
句法
以下语法适用于初始语句:
::= initial
例
以下示例说明了使用初始语句初始化变量以及模拟开始的过程。
Initial
Begin
Areg = 0; // initialize a register
For (index = 0; index < size; index = index + 1)
Memory [index] = 0; //initialize a memory
Word
End
初始模块的另一种用法是对波形描述的规范,该描述执行一次即可为模拟电路的中心部分提供激励。
Initial
Begin
Inputs = 'b000000;
// initialize at time zero
#10 inputs = 'b011001; // first pattern
#10 inputs = 'b011011; // second pattern
#10 inputs = 'b011000; // third pattern
#10 inputs = 'b001000; // last pattern
End
永远封锁
Always块重复执行。仅当模拟终止时,其活动才会终止。对模块中定义的初始块和始终块的数量没有限制。
句法
在整个模拟运行中,always语句会不断重复。 always语句的语法如下所示
::= always
always语句仅在与某种形式的时序控制结合使用时才有用,因为它具有循环性质。
任务与功能
任务和功能是在其他过程中一个或多个位置启用的过程。