SystemVerilog Overriding class members

Overriding class members

Base class or parent class properties and methods can be overridden in the child class or extended class.

Defining the class properties and methods with the same name as parent class in the child class will override the class members.

Overriding class member example

In below example,

The parent class has the method display().
display() method is re-defined in the child class, which will override the parent class method.
c is the handle to the child class, because of override calling c.display will call display method of the child class, not the parent class.

class parent_class;
  bit [31:0] addr;

  function display();
    $display("Addr = %0d",addr);
  endfunction
endclass

class child_class extends parent_class;
  bit [31:0] data;
  function display();
    $display("Data = %0d",data);
  endfunction
endclass

module inheritence;
  initial begin
    child_class c=new();
    c.addr = 10;
    c.data = 20;
    c.display();
  end
endmodule

Simulator Output

Data = 20

Click to execute on

❮ Previous Next ❯

SystemVerilog Polymorphism

Polymorphism in SystemVerilog

Polymorphism means many forms. Polymorphism in SystemVerilog provides an ability to an object to take on many forms.

Method handle of super-class can be made to refer to the subclass method, this allows polymorphism or different forms of the same method.

How,  many forms of a method can be made by referring to the subclass method?
will see with an example,

Polymorphism example

SystemVerilog Polymorphism
SystemVerilog Polymorphism

Let’s write the base_class with a method display();

class base_class;
  virtual function void display();
    $display("Inside base class");
  endfunction
endclass

Writing three extended classes of base_class, with display method overridden in it.

class ext_class_1 extends base_class;
  function void display();
    $display("Inside extended class 1");
  endfunction
endclass

class ext_class_2 extends base_class;
  function void display();
    $display("Inside extended class 2");
  endfunction
endclass

class ext_class_3 extends base_class;
  function void display();
    $display("Inside extended class 3");
  endfunction
endclass

Create an object of each extended class,

ext_class_1 ec_1 = new();
ext_class_2 ec_2 = new();
ext_class_3 ec_3 = new();

Declare an array of a base class,

base_class b_c[3];

Assign extend class handles to base class handles.

b_c[0] = ec_1;
b_c[1] = ec_2;
b_c[2] = ec_3;

Call the display method using base_class handle,

b_c[0].display();
b_c[1].display();
b_c[2].display();

In the above method calls,
Though all the methods are called using base_class handle, different methods are getting called. this shows the many forms of the same method, this is called polymorphism.

Complete code,

// base class 
class base_class;
  virtual function void display();
    $display("Inside base class");
  endfunction
endclass

// extended class 1
class ext_class_1 extends base_class;
  function void display();
    $display("Inside extended class 1");
  endfunction
endclass

// extended class 2
class ext_class_2 extends base_class;
  function void display();
    $display("Inside extended class 2");
  endfunction
endclass

// extended class 3
class ext_class_3 extends base_class;
  function void display();
    $display("Inside extended class 3");
  endfunction
endclass

// module
module class_polymorphism;

  initial begin 
    
    //declare and create extended class
    ext_class_1 ec_1 = new();
    ext_class_2 ec_2 = new();
    ext_class_3 ec_3 = new();
    
    //base class handle
    base_class b_c[3];
    
    //assigning extended class to base class
    b_c[0] = ec_1;
    b_c[1] = ec_2;
    b_c[2] = ec_3;
    
    //accessing extended class methods using base class handle
    b_c[0].display();
    b_c[1].display();
    b_c[2].display();
  end

endmodule

Simulator Output

Inside extended class 1
Inside extended class 2
Inside extended class 3

Click to execute on   

❮ Previous Next ❯

Inheritance in SystemVerilog

SystemVerilog Inheritance

SystemVerilog Inheritance. Inheritance is an OOP concept that allows the user to create classes that are built upon existing classes. The new class will be with new properties and methods along with having access to all the properties and methods of the original class. Inheritance is about inheriting base class members to the extended class.

  • New classes can be created based on existing classes, this is referred to as class inheritance
  • A derived class by default inherits the properties and methods of its parent class
  • An inherited class is called a subclass of its parent class
  • A derived class may add new properties and methods, or modify the inherited properties and methods
  • Inheritance allows re-usability. i.e. derived class by default includes the properties and methods, which is ready to use
  • If the class is derived from a derived class, then it is referred to as Multilevel inheritance
SystemVerilog Inheritance
SystemVerilog Inheritance

Inheritance Terminology

Parent Class

  • It’s an existing class;
  • The class whose features are inherited
  • The parent class is also known as a base class, superclass

Child Class

  • It’s an extended class;
  • The class that inherits the other class is known as subclass
  • The child class is also known as an extended class, derived class, subclass

Inheritance Example

Parent class properties are accessed using child class handle, i.e child class will have (inherit) parent class properties and methods.

In the below example,
parent_class is base class and child_class is written by extending the parent_class.
so child_class is derived from a base class, and it inherits the properties of the parent class.

Though the addr is not declared in child_class, it is accessible. because it is inherited from the parent class.

class parent_class;
  bit [31:0] addr;
endclass

class child_class extends parent_class;
  bit [31:0] data;
endclass

module inheritence;
  initial begin
    child_class c = new();
    c.addr = 10;
    c.data = 20;
    $display("Value of addr = %0d data = %0d",c.addr,c.data);
  end
endmodule

Simulator Output

Value of addr = 10 data = 20

Click to execute on

❮ Previous Next ❯

SystemVerilog deep copy

deep copy

SystemVerilog deep copy copies all the class members and its nested class members. unlike in shallow copy, only nested class handles will be copied. In shallow copy, Objects will not be copied, only their handles will be copied. to perform a full or deep copy, the custom method needs to be added.

In the custom method, a new object is created, all the class properties will be copied to a new handle and the new handle will be returned.

SystemVerilog Deep Copy
SystemVerilog Deep Copy

deep copy example

In the below example, the copy method is added in each class. 
whenever the copy method is called, it will create the new object and copies all the class properties to a new object handle and return the new object handle.

//-- class --- 
class address_range;
  bit [31:0] start_address;
  bit [31:0] end_address  ;

  function new();
    start_address = 10;
    end_address   = 50;
  endfunction
  //copy method
  function address_range copy;
    copy = new();
    copy.start_address = this.start_address;
    copy.end_address   = this.end_address;
    return copy;
  endfunction
endclass

//-- class ---   
class packet;
  //class properties
  bit [31:0] addr;
  bit [31:0] data;
  address_range ar; //class handle

  //constructor
  function new();
    addr  = 32'h10;
    data  = 32'hFF;
    ar = new(); //creating object
  endfunction

  //method to display class prperties
  function void display();
    $display("---------------------------------------------------------");
    $display("\t addr  = %0h",addr);
    $display("\t data  = %0h",data);
    $display("\t start_address  = %0d",ar.start_address);
    $display("\t end_address  = %0d",ar.end_address);
    $display("---------------------------------------------------------");
  endfunction

  //copy method
  function packet copy();
    copy = new();
    copy.addr = this.addr;
    copy.data = this.data;
    copy.ar   = ar.copy;//calling copy function of tr
    return copy;
  endfunction
endclass

// -- module ---
module class_assignment;
  packet pkt_1;
  packet pkt_2;
  initial begin
    pkt_1 = new();   //creating pkt_1 object
    $display("\t****  calling pkt_1 display  ****");
    pkt_1.display();
    pkt_2 = new();   //creating pkt_2 object
    $display("\t****  calling pkt_2 display  ****");
    pkt_2.display();
    pkt_2 = pkt_1.copy(); //calling copy method
    //changing values with pkt_2 handle
    pkt_2.addr = 32'h68;
    pkt_2.ar.start_address = 60;
    pkt_2.ar.end_address = 80;
    $display("\t****  calling pkt_1 display after changing pkt_2 properties ****");
    pkt_1.display();
    $display("\t****  calling pkt_2 display after changing pkt_2 properties ****");
    pkt_2.display();
  end
endmodule

Simulator Output

**** calling pkt_1 display ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 10
end_address = 50
---------------------------------------------------------
**** calling pkt_2 display ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 10
end_address = 50
---------------------------------------------------------
**** calling pkt_1 display after changing pkt_2 properties ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 10
end_address = 50
---------------------------------------------------------
**** calling pkt_2 display after changing pkt_2 properties ****
---------------------------------------------------------
addr = 68
data = ff
start_address = 60
end_address = 80
---------------------------------------------------------

Click to execute on

❮ Previous Next ❯

SystemVerilog Shallow Copy

Shallow Copy

An object will be created only after doing new to a class handle,

packet   pkt_1;
pkt_1  = new();
packet   pkt_2;
pkt_2  = new pkt_1;

In the last statement, pkt_2 is created and class properties were copied from pkt_1 to pkt_2, this is called as “shallow copy”.

Shallow copy allocates the memory, copies the variable values and returns the memory handle.

In shallow copy, All of the variables are copied across: integers, strings, instance handles, etc.

Note::
Objects will not be copied, only their handles will be copied.

to perform the full or deep copy, the custom method can be added.

SystemVerilog Class Shallow Copy
SystemVerilog Class Shallow Copy
SystemVerilog Shallow Copy Limitation
SystemVerilog Shallow Copy Limitation

Shallow copy example

In the below example,

packet class has the properties of bit type and object type (address_range).
after the shallow copy addr, data and handle to ar were copied. As it is shallow copy any changes on pkt_2. ar will reflect in pkt_1.ar (because pkt_2.ar and pkt_1.ar will point to the same object).

//-- class --- 
class address_range;
  bit [31:0] start_address;
  bit [31:0] end_address  ;
  function new();    start_address = 10;
    end_address   = 50;
  endfunction
endclass

//-- class ---   
class packet;
  //class properties
  bit [31:0] addr;
  bit [31:0] data;
  address_range ar; //class handle

  //constructor
  function new();
    addr  = 32'h10;
    data  = 32'hFF;
    ar = new(); //creating object
  endfunction
  //method to display class properties
  function void display();
    $display("---------------------------------------------------------");
    $display("\t addr  = %0h",addr);
    $display("\t data  = %0h",data);
    $display("\t start_address  = %0d",ar.start_address);
    $display("\t end_address  = %0d",ar.end_address);
    $display("---------------------------------------------------------");
  endfunction
endclass

// -- module ---
module class_assignment;
  packet pkt_1;
  packet pkt_2;

  initial begin
    pkt_1 = new();   //creating pkt_1 object
    $display("\t****  calling pkt_1 display  ****");
    pkt_1.display();
 
    pkt_2 = new pkt_1;   //creating pkt_2 object and copying pkt_1 to pkt_2
    $display("\t****  calling pkt_2 display  ****");
    pkt_2.display();

    //changing values with pkt_2 handle
    pkt_2.addr = 32'h68;
    pkt_2.ar.start_address = 60;
    pkt_2.ar.end_address = 80;
    $display("\t****  calling pkt_1 display after changing pkt_2 properties ****");

    //changes made to pkt_2.ar properties reflected on pkt_1.ar, so only handle of the object get copied, this is called shallow copy
    pkt_1.display();
    $display("\t****  calling pkt_2 display after changing pkt_2 properties ****");
    pkt_2.display(); //
  end
endmodule

Simulator Output

**** calling pkt_1 display ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 10
end_address = 50
---------------------------------------------------------
**** calling pkt_2 display ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 10
end_address = 50
---------------------------------------------------------
**** calling pkt_1 display after changing pkt_2 properties ****
---------------------------------------------------------
addr = 10
data = ff
start_address = 60
end_address = 80
---------------------------------------------------------
**** calling pkt_2 display after changing pkt_2 properties ****
---------------------------------------------------------
addr = 68
data = ff
start_address = 60
end_address = 80
---------------------------------------------------------

Click to execute on

Difference between Assignment and Shallow Copy

assignment vs shallow copy
assignment vs shallow copy

❮ Previous Next ❯

SystemVerilog Static Class Members

Static class members

Class members can be created with the keyword static. class members with the keyword static are called as static class members. the class can have static properties and static methods (functions and tasks). a single copy of static variables is shared across multiple instances.

Static Properties

  • The class can have multiple instances, each instance of the class will be having its own copy of variables.
  • Sometimes only one version of a variable is required to be shared by all instances. These class properties are created using the keyword static.

Syntax

static <data_type> <property_name>;

Static Methods

Static methods are the same as static properties,

  • a static method can access only static properties of the class and access to the non-static properties is illegal and lead to a compilation error.
  • Static methods cannot be virtual

Note:
Static class properties and methods can be used without creating an object of that type.

Syntax

static task/function <method_name>;

Static properties example

In the below example,
The class has the variable packet_id, which is the unique ID assigned to the packet;
Static variable no_of_pkts_created, no_of_pkts_created will get incremented on every object creation.

no_of_pkts_created is assigned to packet_id.

class packet;
  
  //class properties
  byte packet_id;
    
  //static property to keep track of number of pkt's created
  static byte no_of_pkts_created;
  
  //constructor
  function new();
    //incrementing pkt count on creating an object
    no_of_pkts_created++;
    packet_id = no_of_pkts_created;
  endfunction
  
  //method to display class prperties
  function void display();
    $display("--------------------------------------");
    $display("\t packet_id  = %0d",packet_id);
    $display("--------------------------------------");
  endfunction 
endclass

module static_properties;
  packet pkt[3];

  initial begin
    foreach(pkt[i]) begin
      pkt[i] = new();
      pkt[i].display();
    end
  end  
endmodule

Simulator Output

--------------------------------------
packet_id  = 1
--------------------------------------
--------------------------------------
packet_id  = 2
--------------------------------------
--------------------------------------
packet_id  = 3
--------------------------------------

Click to execute on

Static method example

Below example shows the declaration of a static function.

class packet;
  
  //class properties
  byte packet_id;
    
  //static property to keep track of number of pkt's created
  static byte no_of_pkts_created;
  
  //constructor
  function new();
    //incrementing pkt count on creating an object
    no_of_pkts_created++;
    packet_id = no_of_pkts_created;
  endfunction
  
  //method to display class prperties
  function void display();
    $display("--------------------------------------");
    $display("\t packet_id  = %0d",packet_id);
    $display("--------------------------------------");
  endfunction 
endclass

module static_properties;
  packet pkt[3];

  initial begin
    foreach(pkt[i]) begin
      pkt[i] = new();
      pkt[i].display();
    end
  end  
endmodule

Simulator Output

--------------------------------------
3 packets created.
--------------------------------------

Click to execute on

Static method trying to access a non-static variable

In the below example,
The static function tries to access the non-static variable of the class, which leads to a compilation error.

class packet;
  byte packet_id;
  
  //static property to keep track of number of pkt's created
  static byte no_of_pkts_created;
  
  //constructor
  function new();
    //incrementing pkt count on creating an object
    no_of_pkts_created++;
  endfunction
    
  //Static method to display class prperties
  static function void display_packets_created();
    $display("--------------------------------------");
    $display("\t Packet Id is %0d",packet_id);
    $display("\t %0d packets created.",no_of_pkts_created);
    $display("--------------------------------------");
  endfunction 
endclass

module static_properties;
  packet pkt[3];

  initial begin
    foreach(pkt[i]) begin
      pkt[i] = new();
    end
    pkt[0].display_packets_created();
  end  
endmodule

Simulator Output

Error-[SV-AMC] Non-static member access
testbench.sv, 19
$unit, "packet_id"
Illegal access of non-static member 'packet_id' from static method
'packet::display_packets_created'.

Click to execute on

Accessing static class properties without creating an object

In the below example,

Static class variable (no_of_pkts_created) and Static class function (display_packets_created) is accessed with class handle which is not constructed (new() is not done).

class packet;
    
  //static property to keep track of number of pkt's created
  static byte no_of_pkts_created;
  
  //constructor
  function new();
    //incrementing pkt count on creating an object
    no_of_pkts_created++;
  endfunction
    
  //Static method to display class prperties
  static function void display_packets_created();
    $display("--------------------------------------");
    $display("\t %0d packets created.",no_of_pkts_created);
    $display("--------------------------------------");
  endfunction 
endclass

module static_properties;
  packet pkt[3];
  packet p;

  initial begin
    foreach(pkt[i]) begin
      pkt[i] = new();
    end
    
    //Accesing static Variable with class handle p
    $display("--------------------------------------");
    $display("\t %0d packets created.",p.no_of_pkts_created);
    $display("--------------------------------------");    
    
    //Accesing static Method with class handle p
    p.display_packets_created();
  end  
endmodule

Simulator Output

--------------------------------------
3 packets created.
--------------------------------------
--------------------------------------
3 packets created.
--------------------------------------

Click to execute on

❮ Previous Next ❯

SystemVerilog Class Constructors

Class Constructors

The new function is called as class constructor.

On calling the new method it allocates the memory and returns the address to the class handle.

SystemVerilog Class Constructor
SystemVerilog Class Constructor
  • The new operation is defined as a function with no return type
  • every class has a built-in new method, calling the constructor of class without the explicit definition of the new method will invoke the default built-in new method
  • specifying return type to the constructor shall give a compilation error (even specifying void shall give a compilation error)
  • The constructor can be used for initializing the class properties. In case of any initialization required, those can be placed in the constructor and It is also possible to pass arguments to the constructor, which allows run-time customization of an object.
SystemVerilog Constructor for Initialization
SystemVerilog Constructor for Initialization

Class Constructor example

class packet;
  //class properties
  bit [31:0] addr;
  bit [31:0] data;
  bit  write;
  string pkt_type;
  //constructor
  function new();
    addr  = 32'h10;
    data  = 32'hFF;
    write = 1;
    pkt_type = "GOOD_PKT";
  endfunction

  //method to display class prperties
  function void display();
    $display("---------------------------------------------------------");
    $display("\t addr  = %0d",addr);
    $display("\t data  = %0h",data);
    $display("\t write = %0d",write);
    $display("\t pkt_type  = %0s",pkt_type);
    $display("---------------------------------------------------------");
  endfunction
endclass

module sv_constructor;
  packet pkt;
  initial begin
    pkt = new();
    pkt.display();
  end
endmodule

Simulator Output

addr = 16
data = ff
write = 1
pkt_type = GOOD_PKT

Click to execute on

❮ Previous Next ❯

this keyword in SystemVerilog

SystemVerilog this keyword

this keyword is used to refer to class properties. this keyword is used to unambiguously refer to class properties or methods of the current instance. this is a pre-defined class handle referring to the object from which it is used, calling this.variable means object.variable.

  • this keyword shall only be used within non-static class methods
  • this keyword refers to the object handle in which it is invoked
this keyword SystemVerilog
this keyword SystemVerilog

this keyword example

In the example below,

The addr, data, write and pkt_type are the property of both class and an argument to the function new, as the name in both are same.this will lead to an ambiguity in assignment and values will not be assigned properly.

class packet;
  
  //class properties
  bit [31:0] addr;
  bit [31:0] data;
  bit   write;
  string  pkt_type;
  
  //constructor
  function new(bit [31:0] addr,data,bit write,string pkt_type);
    addr  = addr;
    data  = data;
    write = write;
    pkt_type = pkt_type;
  endfunction
  
  //method to display class prperties
  function void display();
    $display("---------------------------------------------------------");
    $display("\t addr  = %0h",addr);
    $display("\t data  = %0h",data);
    $display("\t write = %0h",write);
    $display("\t pkt_type  = %0s",pkt_type);
    $display("---------------------------------------------------------");
  endfunction
  
endclass

module sv_constructor;
  packet pkt;

  initial begin
    pkt = new(32'h10,32'hFF,1,"GOOD_PKT");
    pkt.display();
  end
  
endmodule

Simulator Output

addr = 0
data = 0
write = 0
pkt_type =

Click to execute on

SV this keyword example 2

The above problem can be overcome by using “this” keyword to the class properties.

class packet;
  
  //class properties
  bit [31:0] addr;
  bit [31:0] data;
  bit   write;
  string  pkt_type;
  
  //constructor
  function new(bit [31:0] addr,data,bit write,string pkt_type);
    this.addr  = addr;
    this.data  = data;
    this.write = write;
    this.pkt_type = pkt_type;
  endfunction
  
  //method to display class prperties
  function void display();
    $display("---------------------------------------------------------");
    $display("\t addr  = %0h",addr);
    $display("\t data  = %0h",data);
    $display("\t write = %0h",write);
    $display("\t pkt_type  = %0s",pkt_type);
    $display("---------------------------------------------------------");
  endfunction
  
endclass

module sv_constructor;
  packet pkt;

  initial begin
    pkt = new(32'h10,32'hFF,1,"GOOD_PKT");
    pkt.display();
  end
  
endmodule

Simulator Output

addr = 10
data = ff
write = 1
pkt_type = GOOD_PKT

Click to execute on

❮ Previous Next ❯

SystemVerilog classes

SystemVerilog Class

A class is a user-defined data type that includes data (class properties), functions and tasks that operate on data.

functions and tasks are called as methods, both are members of the class.classes allow objects to be dynamically created, deleted, assigned and accessed via object handles.

Class Declaration

Class declaration example

The below class has one data property x and two methods set and get.

class sv_class;
  //class properties
  int x;

  //method-1
  task set(int i);
    x = i;
  endtask

  //method-2
  function int get();
    return x;
  endfunction
endclass

Class Instance and Object Creation

Class declaration/Class Instance

As we know the class is a data type, Declaring class type variable is similar to declaring other variables.

sv_class class_1;

the above statement shows the declaration of variable class_1 with the type sv_class.
In other words, variable class_1 can contain a handle to an instance of the class sv_class.

Object Creation

Class properties and methods can be accessed only after creating the object.

class_1 = new();

the above statement will create an object and assign its handle to class_1.

sv_class class_1 = new();

the above statement will do both declarations of variable and object creation.

Accessing class properties and methods

Class properties and methods can be accessed by using object names followed by property or method name.

class_1.set(10); //calling set method to set value 10 to x
$display("Vlaue of x = %0d",class_1.get(););

Class example

class sv_class;
  //class properties
  int x;

  //method-1
  task set(int i);
    x = i;
  endtask

  //method-2
  function int get();
    return x;
  endfunction
endclass

module sv_class_ex;
 sv_class class_1; //Creating Handle

  initial begin
    sv_class class_2 = new(); //Creating handle and Object
    class_1 = new(); //Creating Object for the Handle
    //Accessing Class methods
    class_1.set(10);
    class_2.set(20);
    $display("\tclass_1 :: Value of x = %0d",class_1.get());
    $display("\tclass_2 :: Value of x = %0d",class_2.get());
  end
endmodule

Simulator Output

class_1 :: Value of x = 10
class_1 :: Value of x = 20

Click to execute on

❮ Previous Next ❯

Task and Function argument passing

Argument Passing

SystemVerilog provides below means for passing arguments to functions and tasks,

  • argument pass by value
  • argument pass by reference
  • argument pass by name
  • argument pass by position

also, functions and tasks can have default argument values.

argument pass by value

In argument pass by value,

the argument passing mechanism works by copying each argument into the subroutine area.

if any changes to arguments within the subroutine, those changes will not be visible outside the subroutine.

argument pass by value example

Variables x and y are passed as an argument in the function call sum, changes to the argument x within the function is not visible outside.

module argument_passing;
  int x,y,z;
  //function to add two integer numbers.
  function int sum(int x,y);
    x = x+y;
    return x+y;   
  endfunction

  initial begin
    x = 20;
    y = 30;
    z = sum(x,y);
    $display("-----------------------------------------------------------------");
    $display("\tValue of x = %0d",x);
    $display("\tValue of y = %0d",y);
    $display("\tValue of z = %0d",z);
    $display("-----------------------------------------------------------------");
  end
endmodule

Simulator Output

-----------------------------------------------------------------
Value of x = 20
Value of y = 30
Value of z = 80
-----------------------------------------------------------------

Click to execute on

argument pass by reference

In pass by reference, a reference to the original argument is passed to the subroutine.

As the argument within a subroutine is pointing to an original argument, any changes to the argument within subroutine will be visible outside.

To indicate argument pass by reference, the argument declaration is preceded by keyword ref.

Any modifications to the argument value in a pass by reference can be avoided by using const keyword before ref, any attempt in changing the argument value in subroutine will lead to a compilation error.

argument pass by reference example

variables x and y are passed as an argument in the function call sum, changes to the argument x within the function, is visible outside.

module argument_passing;
  int x,y,z;

  //function to add two integer numbers.
  function int sum(ref int x,y);
    x = x+y;
    return x+y;   
  endfunction

  initial begin
    x = 20;
    y = 30;
    z = sum(x,y);
    $display("-----------------------------------------------------------------");
    $display("\tValue of x = %0d",x);
    $display("\tValue of y = %0d",y);
    $display("\tValue of z = %0d",z);
    $display("-----------------------------------------------------------------");
  end
endmodule

Simulator Output

-----------------------------------------------------------------
Value of x = 50
Value of y = 30
Value of z = 80
-----------------------------------------------------------------

Click to execute on

Any modifications to the argument value in a pass by reference can be avoided by using const keyword before ref, any attempt in changing the argument value in subroutine will lead to a compilation error.

argument pass by reference with the const keyword

variables x and y are passed as an argument in the function call sum, as arguments are mentioned as const, changes to the argument x within the function leads to a compilation error.

module argument_passing;
  int x,y,z;
  //function to add two integer numbers.
  function int sum(const ref int x,y);
    x = x+y;
    return x+y;   
  endfunction

  initial begin
    x = 20;
    y = 30;
    z = sum(x,y);
    $display("-----------------------------------------------------------------");
    $display("\tValue of x = %0d",x);
    $display("\tValue of y = %0d",y);
    $display("\tValue of z = %0d",z);
    $display("-----------------------------------------------------------------");
  end
endmodule

Simulator Output

'const' variable is either driven or connected to a non-const variable.
Variable 'x' declared as 'const' cannot be used in this context
Source info: x = (x + y);

1 error

Click to execute on

default argument values

The default value can be specified to the arguments of the subroutine.

In the subroutine call, arguments with a default value can be omitted from the call.

if any value is passed to an argument with a default value, then the new value will be considered.

an argument with default value example

variables x, y and z of the subroutine has a default value of 1,2 and 3 respectively, in the function call value is passed only for z. x and y will take the default value.

module argument_passing;
  int q;

  //function to add three integer numbers.
  function int sum(int x=5,y=10,z=20);
    return x+y+z;   
  endfunction

  initial begin
    q = sum( , ,10);
    $display("-----------------------------------------------------------------");
    $display("\tValue of z = %0d",q);
    $display("-----------------------------------------------------------------");
  end
endmodule

Simulator Output

-----------------------------------------------------------------
Value of x = 20
Value of y = 30
Value of z = 25
-----------------------------------------------------------------

Click to execute on

argument pass by name

In argument pass by name, arguments can be passed in any order by specifying the name of the subroutine argument.

argument pass by name example

value to the second argument is passed first by specifying the argument name.

module argument_passing;
  int x,y,z;

  function void display(int x,string y);
    $display("\tValue of x = %0d, y = %0s",x,y);   
  endfunction

  initial begin
    display(.y("Hello World"),.x(2016));
  end
endmodule

Simulator Output

Value of x = 2016, y = Hello World

Click to execute on

❮ Previous Next ❯