SystemVerilog中的local变量

嵌入式技术

1344人已加入

描述

默认情况下,类的成员和方法可从外部访问使用类的对象句柄来访问,也就是说,它们是公共的。

如果我们不希望这样怎么办,即如何组织从外部访问类成员,防止外部其他类意外修改。

在大型项目中,我们可能使用外部提供的基类库(如UVM)。

1. 第三方基类库需要确保它们的用户不能意外修改基类中的成员和方法,目的就是防止对项目的其他部分产生连锁反应。

2. 另外,数据成员仅对拥有该成员的类自身可见也隐藏了实现细节,降低程序的复杂性和提高抽象级别。

用面向对象的语言来描述,就是封装(encapsulation)

在Systemverilog中有两种语法可以实现安全的封装:localprotected

local成员或者方法在类外部不可见,对其扩展类也不可见。只有包含这个成员的类的方法才可以访问这些local成员。

声明一个local成员或者方法的关键词是“local”

 

class packet;
 local int addr; //local property
 
 local function void disp(input int data); //local method
 $display("data = %h", data);
 $display("addr = %h", addr); //access local property
 endfunction
endclass
 
 module class_TOP( );
 initial begin
 packet p1;
 p1 = new( );
 // p1.addr = 'hf;
 //COMPILE ERROR - can't access 'local' property
 // p1.disp(20);
 //COMPILE ERROR - can't access 'local' method
 end
 endmodule

 

在上面的例子中,class “packet”中声明了“local”属性 “addr”和一个local方法“disp”。

因为“addr”是一个 local成员,所以只能够使用类自身声明的方法“disp”访问,所以下面这个访问方式会导致编译错误:

 

p1.addr = ‘hff;
Error-[SV-ICVA] Illegal class variable access
testbench.sv, 25
Local member 'addr' of class 'packet' is not visible to scope 'class_TOP'.
Please make sure that the above member is accessed only from its own class
properties as it is declared as local.

 

同理,由于我们将函数“disp”也声明成了local,所以无法从外部访问这个函数。所以下面的访问方式同样会报编译错误:

 

p1.disp;
Error-[SV-ICMA] Illegal class method access
testbench.sv, 26
Local method 'disp' of class 'packet' is not visible to scope 'class_TOP'.
Please make sure that the above method is called only from its own class
properties as it is declared as local.

 

再看一个例子,扩展类遇到父类中的local成员。

 

 class packet;
 local int addr;
 local function void disp(input int data);
 $display("data = %h", data);
 $display("addr = %h", addr); //access local property
 endfunction
 endclass
 
 class eth_packet extends packet;
 
 function set_addr;
 //addr = 'hf; //COMPILE ERROR -
 //can't access 'local' property from extended class
 endfunction
 
 function void eth_disp;
 //super.disp(50);//COMPILE ERROR -
 //can't access 'local' method from extended class
 endfunction
 
 function void disp(input int data);
 //OK to override 'local' method in extended class
 $display("From eth_packet data=%d", data);
 endfunction
 endclass
 
 module class_TOP( );
 initial begin
 eth_packet e1;
 e1 = new( );
 e1.disp(50);
 end
 endmodule

 

在上面的例子中,我们扩展自父类 “packet”,声明了一个扩展类“eth_packet.”

在类“eth_packet”中直接访问local成员和local方法都会发生编译错误。但是在扩展类中覆盖local成员和方法“disp”是允许的。事实上,方法覆盖之后,访问的已经不是父类中的那个local成员了。


打印log:

 

From eth_packet data= 50
 V C S S i m u l a t i o n R e p o r t

 

  审核编辑:汤梓红

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分