- 重定义问题
在写代码时可能会出现同一个类文件被多个文件调用,为防止仿真器多次编译该类文件需要对类文件进行重定义声明。
在类文件中使用#ifndef 、#define 、#endif 以及#ifdef语句可以避免类文件的重定义。
lab4::packet.sv部分代码如下:
`ifndef INC_PACKET_SV
`define INC_PACKET_SV
calss Packet;
...
endclass:Packet
`endif
#ifndef 宏名 -------代表 if not define 宏,即若没有定义宏,则执行#ifndef与#endif之间的代码,其中#define为定义宏。当编译一次之后宏已经被定义,那么就不会编译第二次,防止重定义的发现。
与#ifndef相反的#ifdef 宏名 ------代表 if define 宏,即若已经定义宏,则执行#ifdef与#endif之间的代码。
#define与#ifnedef(或#ifdef)、#endif组合即可防止重定义,同时还可以采用#else、#elseif等语句。
- 随机化
randomize()用于产生rang类型变量的随机值。
class Packet;
rand bit[3:0] sa, da;
rand logic[7:0] payload[$];
...
constraint valid{
sa inside { [0:15] };
da inside { [0:15] };
payload.size() inside { [2:4] };
}
...
endclass:Packet
上述代码声明了rand类型的sa与da变量,并通过constraint对其范围进行约束,其中inside设置了随机数产生的集合。
在lab4::test.sv中通过调用randomize()函数生成随机数sa、da、payload。
if(!pkt2send.randomize())
...
其中randomize()函数生成随机数,若满足约束则返回1,若不满足约束则返回0.
rand bit[3:0] sa, da;
constraint valid {
sa >5;
da <3;
sa <da;
}
此时调用randomize()函数时,由于不能满足constraint约束,所以返回0.
3.在类之外定义方法
有时候为了保证代码的可读性,会将方法定义在类之外,需要在类内通过extern来声明,在类外通过::(双冒号–作用域操作符)定义方法。
class Packet;
...
extern function new (string name = "Packet");
extern function bit compare (Packet pkt2cmp, ref string message);
extern function void display(string prefix = "NOTE");
...
endclass:Packet
function Packet::new(string name);
...
endfunction:new
function bit Packet::compare(Packet pkt2cmo,ref string message);
...
endfunction:compare
function void Packet::display(string prefix);
...
endfuntion:Packet
在类外进行方法原形定义的时候一定记住添加类名和作用域操作符。