ASIC Verification - Object Oriented Programming
ASIC Verification - Object Oriented Programming
Verification
Object Oriented
Programming
Object Oriented Programming (OOP)
Why OOP?
Helps in creating and maintaining large testbenches:
You can create complex data types and tie them together with the routines that work
with them
Increases productivity:
You can create testbenches and system-level models at a more abstract level by
calling a routine to perform an action rather than toggling bits. You can work with
transactions rather than signal transitions
HDL OOP
Verilog System Verilog
Block definition module Class
Block instance Instance object
Block name Instance name handle
Data Types registers & wires Properties: Variables
behavioral blocks (always, Methods: tasks and
Executable Code
initial), tasks, functions functions
Communication Ports or cross-module task calls, mailboxes,
between blocks calls semaphores, etc.
OOP Basics: Advantages
class BusTran;
function calc_crc;
crc=addr^data.xor; methods
endfuntion: calc_crc
function display;
$display(“BusTran: %h”, addr); methods
endfuntion: display
endclass: BusTran
BusTran b;
b= new();
Call the new function to construct the BusTran object.
Declaring and using a handle When you call new you are allocating a new block of
memory to store variables for that object.
1. new allocates space for BusTran
2. Initializes the variables to their default value (0 for 2
state and x for 4-state variables)
3. Returns the address where the object is stored
BusTran has two 32-bit registers (addr and crc) and an array with 8, 32 bit entries.
How much space would new allocate for an object of BusTran?
class BusTran;
bit [31:0] addr, crc, data[8];
function calc_crc;
crc=addr^data;
endfuntion: calc_crc
function display;
$display(“BusTran: %h”, addr);
endfuntion: display
endclass: BusTran
Class with user defined new function Calling the right new function
class Transaction;
static int count = 0; Number of objects created
int id; Unique instance id
function new();
id = count++; Set id and bump count
endfunction
endclass
Using a id field can help keep track of transactions as they flow through test
Transaction b1,b2;
initial begin
b1=new; //first instance, id=0 First instance id=0, count=1
b2=new; //second instance, id=1 Second instance id=1, count=2
$display(b2.id, b2.count) 1,2
end
•There is only one copy of the static variable count regardless of how many
BusTran objects are created
•The variable id is not static so every BusTran has its own copy
class BusTran;
bit [31:0] addr, crc, data[8];
function void display;
$display(“BusTran”,addr,crc); BusTran b;
endfuntion: display PCITran pc;
endclass: BusTran initial begin
b=new();
b.display();
pc=new();
pc.display();
end
class PCITran;
bit [31:0] addr, data[8];
function void display;
$display(“PCITran: %h”, addr, data);
endfuntion: display
endclass: PCITran
class BusTran;
bit [31:0] addr, src, data[1024], crc;
Statistics stats;
endclass
class Statistics;
time startT, stopT;
static int ntrans=0;
static time total_elapsed_time;
endclass
class Statistics;
time startT, stopT; //Transaction time
static int ntrans=0; //Transaction count
static time total_elapsed_time=0;
class BusTran;
bit [31:0] addr, src, data[1024], crc;
Statistics stats;
function new();
stats=new(); Instantiate the object
endfunction
task create_packet();
// Fill packet with data
stats.start(); Use hierarchical syntax
// Transmit packet
endtask
endclass
a a
j=5 j=50
b1 b2 b2 b2
i=1; i=1; i=10; i=10;
a a a a test=1 test=50
B b1 = new; B b2 = new b1; b2.i = 10; b2.a.j = 50; test = b1.i; test = b1.a.j;
BusTran b1,b2;
b1 = new;
b2 = new;
b2.copy(b1); Deep copy
a a a a
j=5 j=10 j=10
j=5 j=50
b1 b1 b2 b2
i=1; i=1; i=1; i=10;
a a a a test=10 test=50
B b1 = new; b1.a.j = 10; B b2=new; test = b1.a.j; test = b2.a.j;
b2.a.j = 50;
b2.copy(b1)
t1 t1 t1 t2 t2 t2 t2
t2 t1
t1
class Thing;
int data;
endclass
…
Thing t1, t2; // Two handles
initial begin
t1 = new(); // Construct first thing
t1.data = 1;
t2 = new(); // Construct second
t2.data = 2;
t2 = t1; // Second thing is lost
t2.data = 5; // Modifies first thing
$display(t1.data); // Displays “5”
end
• virtual class
A set of classes can be created that can be viewed as being derived from a
common based class
For instance a common base class of the type BasePacket that sets out the
structure of the packet is never instantiated but extended to derive useful
subclasses
Since the base class is not intended to be instantiated it can be made
abstract by specifying it as virtual
BasePacket packets[100];
Now instances of various packet objects can be created and put into the array
For instance packets[1] invokes send method associated with the TokenPacket class
packets[1].send()
• Parameterized classes
It is often useful to define a generic class whose objects can be instantiated to have
different array sizes or data types
The normal verilog parameter mechanism is used to parameterize the class