1.1 logic类型
Verilog中有线网类型(net)和变量类型(variable)这两种,都是四值逻辑的,声明都是类型+声明列表,wire类型只可以被连续赋值,reg只可以被过程赋值,使用reg的时候不一定会生成寄存器,是因为从仿真的角度来看需要一个寄存器来储存变量,和综合过后的电路没有直接的联系。
Systemverilog里面也是网类型(net)和变量类型(variable)这两种,声明的方式为:类型+数据类型+声明列表,线网的类型一般有wire、tri、wand、wor等等,变量类型只需要关键字var即可,而且var还是可以省略的。SV对reg数据类型进行了改动,除了可以作为一个变量以外还可以被连续赋值、门单元和模块所驱动,称为logic,任何可以使用线网的地方都可以使用logic,但是要求logic不能拥有多个结构性驱动。
logic使用的场景如果是验证的话,那么他只会作为单纯的变量进行赋值,这些变量也只属子软件环境构建。因为SV作为侧重验证的语言、并不十分关切logi对应的逻辑应该被综合为寄存器还是线网。logic被推出的另外一个原因也是为子方便验证人员驱动和连接硬件模块、而省去考虑究竟该使用reg还是wire的精力。这既节省了时间,也避免了出错的可能。
在SV里面连续赋值的左值支持变量类型,而Verilog里面仅支持线网类型。
1.2 二值变量和四值变量
四状态的默认值是x,双状态的默认值是0,但是线网的没有驱动的情况下输出是Z;将四值变量赋值给二值变量X和Z值会转变为0,可以利用$inunknown(变量名)来检查表达式里面是否有X或者Z
1.3 有符号和无符号、四值逻辑和二值逻辑
四值逻辑类型 | integer、logic、reg、net-type |
二值逻辑类型 | byte、shortint、longint、int、bit |
有符号类型 | byte、short、int、longint、integer |
无符号类型 | bit、logic、reg、net-type |
在进行不同数据类型操作的时候荧光着重注意变量的:逻辑数值类型、符号类型、矢量位宽
1.4 固定数组
定宽数组:
int lo_hi [0:15];
int array2 [0:7] [0:3]; //多维数组
初始化和赋值:
常量数组:单引号+大括号=初始化数组
int ascend [4] =`{0,1,2.3}
同时使用为下标和数组下标:
initial begin
bit [31:0] scr[5] =`{5[5]};
display ( scr[0],, //'b101
scr[0][0],, //'b1
scr[0][2:1] //'b10
)
end
1.5 合并数组
数组格式大小必须是[msb:lsb],而不是 [size].
合并数组:
int [3:0] [7:0] a;
非合并数组:[7:0]是列,[3:0]是行
int [7:0] a [3:0];
1.6 动态数组
动态数组再声明的时候使用的空的下标,表明数组的宽度不在编译时给出,而是在程序运行的时候再指明。使用new[ ] 来分配空间。
//动态数组保存元素数量不定的列表
bit [7:0] mask [ ] = `{8'b0000_0000, 8'b0000_0001, 8'b0000_0011, 8'b0000_0111,
8'b0000_1111, 8'b0001_1111, 8'b0011_1111, 8'b0111_1111,
8'b1111_1111 };
1.7 队列
队列的声明是使用带有美元符号的下标,结合了链表和数组的优点,可以在任何一个队列中增加或者删除元素,在性能损失上会小很多。
q[$]={0,2,5};
1.8 关联数组
关联数组采用在方括号中放置数据类型的形式进行声明。
initial begin
bit [63:0] assoc[bit[63:0]],idx=1;
repeat(64) begin
assoc[idex]=idex;
idex=idex<<1;
end
end
1.9 数组操作
for和foreach:
复制和比较: