0% found this document useful (0 votes)
29 views

Unit 3

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
29 views

Unit 3

Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 66

Digital Design and Verification with System Verilog

Year/Sem Sub. Code PROFESSIONAL ELECTIVE-II L T P/D C


IV-I 7C723 Digital Design and Verification with System Verilog 3 - - 3

Course Description:
This course gives a student an in-depth introduction to the main System Verilog enhancements to the Verilog hardware
description language (HDL), discusses the benefits of the new features, and demonstrates how design and verification can
be more efficient and effective when using System Verilog constructs.
The course is broken down into two modules: The Design module examines improvements for RTL design and synthesis;
the Verification module explores verification enhancements such as object-oriented design, assertions and randomization.

Prerequisites:
• A working knowledge of Verilog HDL
• The ability to navigate a file system and use a text editor
• A basic understanding of digital hardware design and verification
Unit-3: System Verilog Language Concepts

• Evolution of System Verilog : Differences between Verilog and


System Verilog HDL.
• New features added in System Verilog (New Data type additions,
Arrays - Fixed, Packed, Dynamic, Queues, Associated, Structures &
Unions,
• New Operators, New additions to Subroutines, New additions to
Procedural statements & Control flow,
• Concurrency: Fork.join, Fork..join_any, Fork..join_none, Automatic
Variables, Interfaces, Program block).
Verilog HDL and System Verilog
Difference between Verilog and SystemVerilog :

S.No. VERILOG SYSTEM VERILOG


SystemVerilog is a combination of both
Verilog is a Hardware Description Language
01. Hardware Description Language (HDL) and
(HDL).
Hardware Verification Language (HVL).
SystemVerilog language is used to model,
Verilog language is used to structure and
02. design, simulate, test and implement
model electronic systems.
electronic system.
It supports structured and object oriented
03. It supports structured paradigm.
paradigm.
SystemVerilog is based on class level
04. Verilog is based on module level testbench.
testbench.
05. It is standardized as IEEE 1364. It is standardized as IEEE 1800-2012.
Verilog HDL and System Verilog
Difference between Verilog and SystemVerilog :

S.No. VERILOG SYSTEM VERILOG


SystemVerilog is based on Verilog,
Verilog is influenced by C language
06. VHDL and c++ programming
and Fortran programming language.
language.
07. It has file extension .v or .vh It has file extension .sv or .svh
It supports various datatypes like
08. It supports Wire and Reg datatype.
enum, union, struct, string, class.
09. It is based on hierarchy of modules. It is based on classes.
It was began in 1983 as proprietary It was originally intended as an
10.
language for hardware modelling. extension to Verilog in the year 2005.
System Verilog offers many improved data structures compared with Verilog.

Some of these were created for designers but are also useful for testbenches.

In this chapter you will learn about the data structures most useful for verification.

System Verilog introduces new data types with the following benefits.

Ø Two-state: better performance, reduced memory usage


Ø Queues, dynamic and associative arrays and automatic storage: reduced
memory usage, built-in support for searching and sorting
Ø Unions and packed structures: allows multiple views of the same data
Ø Classes and structures: support for abstract data structures
Ø Strings: built-in string support
Ø Enumerated types: code is easier to write and understand
System Verilog Data Types
System Verilog introduces several new data types. Many of these will be familiar to C
programmers.
The idea is that algorithms modelled in C can more easily be converted to System Verilog if
the two languages have the same data types.

Verilog’s variable types are four-state: each bit is 0,1,X or Z. System Verilog introduces
new two-state data types, where each bit is 0 or 1 only.

You would use these when you do not need X and Z values, for example in test benches and
as for-loop variables.

Using two-state variables in RTL models may enable simulators to be more efficient. Used
appropriately, they should not affect the synthesis results.
System Verilog - Two-state types
System Verilog introduces several two-state data types to improve simula- tor performance and
reduce memory usage, over four-state types. The simplest type is the bit, which is always
unsigned. There are four signed types: byte, shortint, int, and longint.
TYPE Description Example
bit user-defined size bit [3:0] a_nibble;
byte 8 bits, signed byte a, b;
shortint 16 bits, signed shortint c, d;
int 32 bits, signed int i,j;
longint 64 bits, signed Longint lword;

Example 2-2 Signed data types


bit b; // 2-state, single-bit
bit [31:0] b32; // 2-state, 32-bit unsigned integer
int i; // 2-state, 32-bit signed integer
byte b8; // 2-state, 8-bit signed integer
shortint s; // 2-state, 16-bit signed integer
longint l; // 2-state, 64-bit signed integer
System Verilog Data Types
Note that, unlike in C, System Verilog specifies the number of bits for the fixed-width types.

TYPE Description Example


reg user-defined size reg [7:0] a_byte;

logic identical to reg in every way logic [7:0] a_byte;

integer 32 bits, signed integer i, j, k;


System Verilog Data Types
logic is a better name than reg, so is preferred. As we shall see, you can use logic where in the past you have
may have used reg or where you may have used wire.

TYPE Description Example


time 64-bit unsigned time now;

shortreal like float in C shortreal f;

real like double in C real g;

realtime identical to real realtime now;


System Verilog - Arrays
In Verilog-1995, you could define scalar and vector nets and variables. You could also
define memory arrays, which are one-dimensional arrays of a variable type. Verilog-2001
allowed multi-dimensioned arrays of both nets and variables, and removed some of the
restrictions on memory array usage.

System Verilog takes this a stage further and refines the concept of arrays and permits more
operations on arrays.
In System Verilog, arrays may have either packed or unpacked dimensions, or both. Consider
this example:

reg [3:0][7:0] register [0:9];


System Verilog - Arrays reg [3:0][7:0] register [0:9];
By contrast, unpacked dimensions can be arranged in memory in any way that the simulator chooses. You can
reliably copy an array on to another array of the same type.

For arrays with different types, you must use a cast, and there are rules for how an unpacked type is cast to a
packed type. Unpacked arrays can be any type, such as arrays of reals.

SystemVerilog permits a number of operations on complete unpacked arrays and slices of unpacked arrays.
For these, the arrays or slices involved must have the same type and the same shape – i.e. exactly the same
number and lengths of unpacked dimensions.

The packed dimensions may be different, as long as the array or slice elements have the same number of bits.

The permitted operations are:


Ø Reading and writing the whole array
Ø Reading and writing array slices
Ø Reading and writing array elements
Ø Equality relations on arrays, slices and elements
System Verilog - Arrays reg [3:0][7:0] register [0:9];

System Verilog also includes dynamic arrays (the number of elements may change during
simulation) and associative arrays (which have a non-contiguous range).

To support all these array types, System Verilog includes a number of array querying
functions and methods.

For example, you could use $dimensions to find the number dimensions of an array
variable.
System Verilog - Fixed-Size Arrays
System Verilog offers several flavors of arrays beyond the single-dimension, fixed-size
Verilog-1995 arrays. Many enhancements have been made to these classic arrays.
Verilog requires that the low and high array limits must be given in the declaration.
Almost all arrays use a low index of 0, so System Verilog lets you use the shortcut of just giving the array size,
similar to C:

Example 2-4 Declaring fixed-size arrays


int lo_hi[0:15]; // 16 ints [0]..[15]
int c_style[16]; // 16 ints [0]..[15]

You can create multidimensional fixed-size arrays by specifying the dimensions after the variable name.
This is an unpacked array; packed arrays are shown later.
The following creates several two-dimensional arrays of integers, 8 entries by 4, and sets the last entry to 1.
Multidimensional arrays were introduced in Verilog-2001, but the compact declarations are new.
System Verilog - Fixed-Size Arrays
System Verilog offers several flavors of arrays beyond the single-dimension, fixed-size
Verilog-1995 arrays. Many enhancements have been made to these classic arrays.

Example 2-5 Declaring and using multidimensional arrays


int array2 [0:7][0:3]; // Verbose declaration
int array3 [8][4]; // Compact declaration
array2[7][3] = 1; // Set last array element

System Verilog stores each element on a longword (32-bit) boundary. So a byte,


shortint, and int are all stored in a single longword, while a long- int
is stored in two longwords. (Simulators frequently store four-state types such as
logic and integer in two or more longwords.)
System Verilog - Fixed-Size Arrays
System Verilog - Array Literal
Basic array operations — for and foreach
The most common way to manipulate an array is with a for or foreach loop. In Example 2-8, the variable i
is declared local to the for loop. The System Verilog function $size returns the size of the array. In the
foreach statement, you specify the array name and an index in square brackets, and System Verilog
automatically steps through all the elements of the array. The index variable is local to the loop.
Basic array operations — for and foreach
Note that the syntax of the foreach statement for multidimensional arrays may not be what you expected!
Instead of listing each subscript in separate square brackets – [i][j] – they are combined with a comma – [i,j].
Basic array
operations —
for and foreach
Note that the syntax of the
foreach statement for
multidimensional arrays may not
be what you expected! Instead
of listing each subscript in
separate square brackets – [i][j]
– they are combined with a
comma – [i,j].
System Verilog - Typedef
Typedef

SystemVerilog’s data type system allows you to define quite complex types. To make this kind
of code clear, the typedef facility was introduced. Typedef allows users to create their own
names for type definitions that they will use frequently in their code. Typedefs can be very
convenient when building up complicated array definitions.

typedef reg [7:0] octet; is the same as reg [7:0] b;


octet b;

typedef octet [3:0]


quadOctet; is the same as reg [3:0][7:0] qBytes [1:10];
quadOctet qBytes [1:10];
System Verilog - Enum
Enum
System Verilog also introduces enumerated types, for example

enum { circle, ellipse, freeform } c;


Enumerations allow you to define a data type whose values have names. Such data types
are appropriate and useful for representing state values, opcodes and other such non-
numeric or symbolic data.

Typedef is commonly used together with enum, like this:

typedef enum { circle, ellipse, freeform } ClosedCurve;


ClosedCurve c;
c = 2; // ERROR
System Verilog - Enum
c = ClosedCurve'(2); // Casting – okay
The named values of an enumeration type act like constants.

The default type is int. You can copy them to and from variables of the enumeration type,
compare them with one another and so on. Enumerations are strongly typed.

You can’t copy a numeric value into a variable of enumeration type, unless you use a type-
cast:

However, when you use an enumeration in an expression, the value you are working with
is the literal’s integer equivalent; so, for example, it’s okay to compare an enumeration
variable with an integer; and it’s okay to use an enumeration value in an integer
expression.
System Verilog - Struct and Union struct {
System Verilog introduces struct and union data int x, y;
types, similar to those in C.
} p;

Struct members are selected using the .name syntax: p.x = 1;

Structure literals and expressions may be formed using braces. p = {1,2};

It is often useful to declare a new structure type typedef struct packed {


using typedef and then declare variables using the int x, y;
new type. Note also that structs may be packed. } Point;
Point p;
Unions are useful where the same hardware resources (like a register) can store values of
different types (e.g. integer, floating point, …)
System Verilog New Operators
System Verilog adds a number of new operators, mostly borrowed from C.

These include increment (++) and decrement (--), and assignment operators (+=, -=, ...).
The wild equality operators (=== and !==) act like the comparisons in a casex statement, with
X and Z values meaning “don’t care”.

New loop statements


Also from C is the do-while loop statement and break and continue.

The new foreach loop is used with array variables.


The for loop has been enhanced, so that the following is permitted:

for (int i = 15, logic j = 0 ; i > 0 ; i--, j = ~j) ...


Combinational Logic using SV Gate Models
• Combinational logic is stateless: Changes in inputs are immediately
reflected by changes in outputs.
Queues
• A queue is a variable-size, ordered collection of homogeneous
elements.
• like a dynamic array, queues can grow and shrink
• queue supports adding and removing elements anywhere
• Queues are declared using the same syntax as unpacked arrays, but
specifying $ as the array size.
• In queue 0 represents the first, and $ representing the last entries.

A queue can be bounded or unbounded


•bounded queue – queue with the number of entries limited or queue size specified
•unbounded queue – queue with unlimited entries or queue size not specified
Queue Declaration
data_type queue_name[$];
where:
data_type – data type of the queue elements.
queue_name – name of the queue.
Examples
bit queue_1[$]; // queue of bits (unbound queue)
int queue_2[$]; // queue of int
byte queue_3[$:255]; // queue of byte (bounded queue with 256 entries)
string queue_4[$]; // queue of strings
Queue Initialization
• queue_1 = {0,1,2,3};
• queue_4 = {“Red”, "Blue”, "Green”};

Unbounded Queue

Queue with n elements


Queue Initialization
• queue_1 = {0,1,2,3};
• queue_4 = {“Red”, "Blue”, "Green”};

Bounded Queue

Queue with 8 elements


Queue Methods
Method Description
size() returns the number of items in the queue
insert() inserts the given item at the specified index position
delete() deletes the item at the specified index position
push_front() inserts the given element at the front of the queue
push_back() inserts the given element at the end of the queue
pop_front() removes and returns the first element of the queue
pop_back() removes and returns the last element of the queue
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method
module queues_array; //Delete Method
//declaration queue_2.delete(3);
bit [31:0] queue_1[$]; //unbounded queue $display("----- Queue_2 size after Delete is %0d ---",queue_2.size());
string queue_2[$]; foreach(queue_2[i])$display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
end
initial begin
//Queue Initialization: endmodule
queue_1 = {0,1,2,3};
queue_2 = {"Red","Blue","Green"};

//Size-Method
$display("----- Queue_1 size is %0d -----",queue_1.size());
foreach(queue_1[i]) $display("\tqueue_1[%0d] = %0d",i,queue_1[i]);
$display("----- Queue_2 size is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);

//Insert-Method
queue_2.insert(1,"Orange");
$display("----- Queue_2 size after inserting Orange is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method
module queues_array; //Delete Method
//declaration queue_2.delete(3);
bit [31:0] queue_1[$]; //unbounded queue $display("----- Queue_2 size after Delete is %0d ---",queue_2.size());
string queue_2[$]; foreach(queue_2[i])$display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
end
initial begin
//Queue Initialization: endmodule
queue_1 = {0,1,2,3};
queue_2 = {"Red","Blue","Green"};

//Size-Method
$display("----- Queue_1 size is %0d -----",queue_1.size());
foreach(queue_1[i]) $display("\tqueue_1[%0d] = %0d",i,queue_1[i]);
$display("----- Queue_2 size is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);

//Insert-Method
queue_2.insert(1,"Orange");
$display("----- Queue_2 size after inserting Orange is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method
module queues_array; //Delete Method
//declaration queue_2.delete(3);
bit [31:0] queue_1[$]; //unbounded queue $display("----- Queue_2 size after Delete is %0d ---",queue_2.size());
string queue_2[$]; foreach(queue_2[i])$display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
end
initial begin
//Queue Initialization: endmodule
queue_1 = {0,1,2,3};
queue_2 = {"Red","Blue","Green"};

//Size-Method
$display("----- Queue_1 size is %0d -----",queue_1.size());
foreach(queue_1[i]) $display("\tqueue_1[%0d] = %0d",i,queue_1[i]);
$display("----- Queue_2 size is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);

//Insert-Method
queue_2.insert(1,"Orange");
$display("----- Queue_2 size after inserting Orange is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method
module queues_array; //Delete Method
//declaration queue_2.delete(3);
bit [31:0] queue_1[$]; //unbounded queue $display("----- Queue_2 size after Delete is %0d ---",queue_2.size());
string queue_2[$]; foreach(queue_2[i])$display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
end
initial begin
//Queue Initialization: endmodule
queue_1 = {0,1,2,3};
queue_2 = {"Red","Blue","Green"};

//Size-Method
$display("----- Queue_1 size is %0d -----",queue_1.size());
foreach(queue_1[i]) $display("\tqueue_1[%0d] = %0d",i,queue_1[i]);
$display("----- Queue_2 size is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);

//Insert-Method
queue_2.insert(1,"Orange");
$display("----- Queue_2 size after inserting Orange is %0d -----",queue_2.size());
foreach(queue_2[i]) $display("\tqueue_2[%0d] = %0s",i,queue_2[i]);
Queue Methods Example
Queue, push_front(), push_back(), pop_front() and pop_back() Method
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method
module queues_array; //Pop_front Method
//declaration lvar = queue_1.pop_front();
bit [31:0] queue_1[$]; $display("\tQueue_1 pop_front value is %0d",lvar);
int lvar;
//Pop_back Method
initial begin lvar = queue_1.pop_back();
//Queue Initialization: $display("\tQueue_1 pop_back value is %0d",lvar);
queue_1 = {0,1,2,3}; end
endmodule
//Size-Method
$display("\tQueue_1 size is %0d",queue_1.size());

//Push_front Method
queue_1.push_front(22);
$display("\tQueue_1 size after push_front is %0d",queue_1.size());

//Push_back Method
queue_1.push_back(44);
$display("\tQueue_1 size after push_back is %0d",queue_1.size());
Queue Methods Example
Bounded queue declaration and accessing

The number of entries of the bounded queue is limited, push_back to the


bounded queue (after the queue full condition) will not impact any changes to the
queue. push_front to the bounded queue (after the queue full condition) will
delete the last entry from queue and stores a new entry in the 0th index of the
queue.
Queue Methods Example
Unbounded Queue Declaration, Initialization, Size, Insert and Delete Method

module queues_array; $display("After push_front Queue elements are,");


//declaration $display("\tqueue = %p",queue);
int queue[$:2]; end
int index;
endmodule
int temp_var;

initial begin
//Queue Initialization:
queue = {7,3,1};

$display("Queue elements are,");


$display("\tqueue = %p",queue);

queue.push_back(10);

$display("After push_back Queue elements are,");


$display("\tqueue = %p",queue);

queue.push_front(10);
Queue Methods Example
Deleting complete queue
Calling queue.delete() method will delete the complete queue, which leads to the deletion of all the entries
of the queue.
module qu_delete;
//queue declaration
int qu[$];

initial begin

qu.push_back(2);
qu.push_back(13);
qu.push_back(5);
qu.push_back(65);

$display("[Before-Delete] Queue size is %0d",qu.size());


qu.delete();
$display("[After -Delete] Queue size is %0d",qu.size());

end
endmodule
System Verilog Processes – fork_join
Fork-Join will start all the processes inside it parallel and wait for the completion of all the processes.

At start of simulation
statements 1 and 2 are
executed sequentially

Processes inside fork-


join gets executed
parallely

Statements 3 and 4 will get


executed after completion of
the process inside fork-join
fork_join example
In below example,

fork block will be blocked until the completion of process-1


and Process-2.

Both process-1 and Process-2 will start at the same time,


Process-1 will finish at 5ns and Process-2 will finish at 20ns.
fork-join will be unblocked at 20ns.
System Verilog Processes – fork-join_any
Fork-Join_any will be unblocked after the completion of any of the Processes.

At start of simulation
statements 1 and 2 are
executed sequentially

fork block will be


blocked until the
completion of any of the
Process

After Processes 2 completion inside fork-


join_any
-- Statements 3 and 4 will get executed
fork-join_any Example
In the below example,
fork block will be blocked until the completion of any of
the Process Process-1 or Process-2.

Both Process-1 and Process-2 will start at the same time,


Process-1 will finish at 5ns and Process-2 will finish at
20ns.

fork-join_any will be unblocked at 5ns.


System Verilog Processes – fork-join_none
As in the case of Fork-Join and Fork-Join_any fork block is blocking, but in case of Fork-Join_none fork block will be non-
blocking.

At start of simulation
statements 1 and 2 are
executed sequentially

Processes inside the fork-join_none block


will be started at the same time, fork
block will not wait for the completion of
the Process inside the fork-join_none.

-- Statements 3 and 4 will get executed


and not wait for processes to complete
Wait_fork Example - 1
wait fork; causes the process to block until the
completion of all processes started from fork blocks.
In the below example,
after the completion of Process-1 (i.e, after 5ns)
fork-join_any will get unblocked, the $finish will get
called and it ends the simulation.

The simulation will get ended in the middle of the


execution of process-2, this can be avoided with the
use of wait-fork.
Wait_fork Example - 2
In the below example,
wait fork will wait for the
completion of the second thread
in the fork-join_any.

for better understanding compare


the result of Example-1 and
Example-2
Tasks and Functions
• Tasks and functions provide the ability to execute common
procedures from several different places in a description.

• They also provide a means of breaking up large procedures into


smaller ones to make it easier to read and debug the source
descriptions.

• Input, output, and inout argument values can be passed into and
out of both tasks and functions.
Distinctions Between Tasks and Functions
The following rules distinguish tasks from functions:
– A function must execute in one simulation time unit; a task can contain
time-controlling statements.
– A function cannot enable a task; a task can enable other tasks and
functions.
– A function must have at least one input argument; a task can have zero or
more arguments of any type.
– A function returns a single value; a task does not return a value.

The purpose of a function is to respond to an input value by returning a single value.


A task can support multiple goals and can calculate multiple result values
Tasks and Functions

• Tasks and Functions provide a means of splitting code into small


parts.
• A Task can contain a declaration of parameters, input arguments,
output arguments, in-out arguments, registers, events, and zero or
more behavioral statements.
• SystemVerilog task can be,
– static
– automatic
Tasks and Functions
• Static tasks
– Static tasks share the same storage space for all task calls.
• Automatic tasks
– Automatic tasks allocate unique, stacked storage for each task call.
System Verilog allows,
o to declare an automatic variable in a static task
o to declare a static variable in an automatic task
o more capabilities for declaring task ports
o multiple statements within task without requiring a begin…end or fork…join block
o returning from the task before reaching the end of the task
o passing values by reference, value, names, and position
o default argument values
o the default direction of argument is input if no direction has been specified
o default arguments type is logic if no type has been specified
Tasks Examples
task arguments in declarations and mentioning directions
task arguments in parentheses
Task Example Illustrates the use of tasks for the traffic light sequencer
Functions
• A Function can contain declarations of range, returned type,
parameters, input arguments, registers, and events.
• A function without a range or return type declaration returns a one-
bit value
• Any expression can be used as a function call argument
• Functions cannot contain any time-controlled statements, and they
cannot enable tasks
• Functions can return only one value

SystemVerilog function can be,


– static
– automatic
Functions
• Static Function
– Static functions share the same storage space for all function calls.
• Automatic Function
– Automatic functions allocate unique, stacked storage for each function call.

SystemVerilog allows,
– to declare an automatic variable in static functions
– to declare the static variable in automatic functions
– more capabilities for declaring function ports
– multiple statements within a function without requiring a begin…end or fork…join block
– returning from the function before reaching the end of the function
– Passing values by reference, value, names, and position
– default argument values
– function output and inout ports
– the default direction of argument is input if no direction has been specified.
– default arguments type is logic if no type has been specified.
Functions
function arguments in declarations and mentioning directions
function arguments in parentheses
Functions
function with return value with the return keyword
In this example,
arguments in declarations and directions, return
value is specified using the return statement.
Functions
Void function Example
The example shows usage of void function, void function,(function with no return value)
Functions
discarding function return value
The function return value must be assigned to a variable or used in an expression.
Calling a function without return value assigned to a variable can result in a warning message.
SystemVerilog void data type is used to discard a function’s return value without any warning message.
Functions
function call as an expression
Task and Function 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.


Task and Function argument passing
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.
Task and Function argument passing
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.
Task and Function argument passing
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.

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.
Task and Function argument passing
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.
Task and Function argument passing
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.
Task and Function argument passing
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.

You might also like