0% found this document useful (0 votes)
150 views20 pages

Verification Testbench: Nagesh Loke ARM CPU Verification Lead/Manager

The document discusses the components and design of a verification testbench, including how it provides an environment to test and verify a design using stimulus, checkers, and coverage, and highlights the complexity involved in building a testbench that can thoroughly verify a system like a CPU. It provides examples of how past approaches to building testbenches were limited and outlines a better approach using SystemVerilog that allows modular, reusable, and randomized testing of a design.

Uploaded by

arunsrl
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)
150 views20 pages

Verification Testbench: Nagesh Loke ARM CPU Verification Lead/Manager

The document discusses the components and design of a verification testbench, including how it provides an environment to test and verify a design using stimulus, checkers, and coverage, and highlights the complexity involved in building a testbench that can thoroughly verify a system like a CPU. It provides examples of how past approaches to building testbenches were limited and outlines a better approach using SystemVerilog that allows modular, reusable, and randomized testing of a design.

Uploaded by

arunsrl
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/ 20

Verification Testbench

Nagesh Loke
ARM CPU Verification Lead/Manager

1
What to expect?

▪ This lecture aims to:


▪ provide an idea of what a testbench is
▪ help develop an understanding of the various components of a testbench
▪ build an appreciation of the complexity in a testbench
▪ highlight why it is as much a software problem as is a hardware problem

2
What is a testbench?
▪ A testbench helps build an environment to test and verify a design
▪ The key components of a testbench are:
▪ Stimulus
▪ is used to drive inputs of the design to generate a high-level of confidence
▪ should be able to exercise all normal input scenarios and a good portion of critical combinations
with ease
▪ Checker
▪ is a parallel & independent implementation of the specification
▪ is used verify the design output against the modeled output
▪ Coverage
▪ Helps measure quality of stimulus
▪ Provides a measure of confidence to help determine closure of verification effort

3
What are we verifying? opcode[2:0]

▪ An ALU has
▪ an input clock
A[7:0]
▪ two 8-bit inputs as operands
▪ a 3-bit opcode as an operator
▪ a 16-bit output
OUT [15:0]

▪ Performs the following operations:


▪ ADD, SUB, AND, OR, XOR, MUL, XNOR

B[7:0]

clk

4
How was it done in the past?

What are some of the


issues with this approach?

5
What should the approach be?
▪ Start with a Verification plan
▪ A Verification plan talks about:
▪ various design features and scenarios that need to be tested
▪ architecture of the testbench
▪ reuse in higher level testbenches

▪ Testbench should have the ability to:


▪ test as many input data and opcode combinations as possible
▪ test different orders of opcodes
▪ stress key features/combinations
▪ use more machine time and less human time

6
SystemVerilog
▪ SystemVerilog as a hardware verification language provides a rich set of features
▪ Data Types & Aggregate data types
▪ Class, Event, Enum, Cast, Parameterization, Arrays, Associative arrays, Queues and manipulating methods
▪ OOP functionality
▪ Classes, Inheritance, Encapsulation, Polymorphism, memory management
▪ Processes
▪ fork-join control, wait statements
▪ Clocking blocks
▪ Interprocess synchronization & communication
▪ Semaphores, Mailboxes, named events
▪ Assertions
▪ Functional Coverage
▪ Virtual Interfaces
▪ Constraints

7
Components of a testbench
▪ The ALU testbench module now looks
different
▪ It includes headers for various components
▪ ALU Interface
▪ ALU Transaction
▪ ALU Monitor
▪ ALU BFM (driver)
▪ ALU Scoreboard
▪ It creates the interfaces
▪ It instantiates the DUT

8
Main Test
▪ A program block is the main entry point
▪ A bfm object and a scoreboard object are
created
▪ All the components are started
▪ A fork/join process ensures that they all
start in parallel
▪ We exit the fork statement at 0 time
▪ Simulation is stopped when $finish is called
▪ Multiple initial blocks execute in parallel

9
Transaction class

▪ The ALU transaction class:


▪ Uses an enum type for optype
▪ Uses “rand” to declare inputs that need
to be driven with random values
▪ Has a print utility that can be used with a
transaction handle/object

10
BFM/driver
▪ The BFM/driver class:
▪ Has a handle to a virtual interface
▪ Declares a alu_trxn data type
▪ Has a constructor
▪ drive() task:
◦ Does not end
◦ Creates a new transaction
◦ Randomizes the transaction
◦ Passes the handle to drive_trxn() task
▪ drive_trxn () task
◦ consumes time
◦ drives the input signals based on the values in the
trxn class
◦ Uses clocking block and non-blocking assignments
◦ Adheres to pin level timing of signals

11
Scoreboard
▪ The Scoreboard:
▪ Functionality is to continuously check the output
independent of the input stimulus
▪ check() task:
◦ Collects information from the interface and
populates the trxn class
◦ Calls a compute_expected_out function
▪ compute_expected_out() task
◦ Implements the model of the deisign
◦ Takes in the inputs and gets an expected output
◦ Compares the actual output against the expected
output
◦ Issues an error message if the comparison fails

12
How does the testbench look like?
alu_tb
clock Process control
generation logic logic

clk
A OUT
alu_bfm ALU
ALU
B

alu_sb

13
How do we know we are done?

▪ With a random testbench it is difficult to know what scenarios have been exercised
▪ Two techniques are typically used to get a measure of what’s done
▪ Code Coverage
▪ No additional instrumentation is needed
▪ Toggle, Statement, Expression, Branch coverage
▪ Functional Coverage
▪ Requires planning
▪ Requires instrumenting code
▪ SystemVerilog provide constructs to support functional coverage
▪ Provides detailed reports on how frequently coverage was hit with the test sample
▪ Coverage closure is an important aspect of verification quality

14
What did we go over …

▪ Built a directed and random testbench


▪ Discussed various components of a testbench
▪ Modularized and built in complexity into a testbench … for a reason
▪ Demonstrated that verification and testbench development requires good planning and
software skills

15
ARM Cortex A72 CPU

16
ARM CCN-512 SoC Framework

17
What are the challenges of verifying complex systems?

▪ Typical processor development from scratch could be about 100s of staff years effort
▪ Multiple parallel developments, multiple sites and it takes a crowd to verify a processor
▪ The challenges are numerous – especially when units are put together as a larger unit
or a whole processor and verified
▪ Reuse of code becomes an absolute key to avoid duplication of work
▪ Multiple times it is essential to integrate an external IP into your system
▪ The IP can come with it’s own verification implementation
▪ This requires rigorous planning, code structure, & lockstep development
▪ Standardization becomes a key consideration

▪ So how do we solve this?

18
Useful pointers

▪ https://verificationacademy.com/
▪ SV Unit YouTube Video
▪ EDA Playground
▪ http://testbench.in/
▪ Search for SystemVerilog on YouTube

19
Let’s solve this …
class base; program a;
int a; initial begin
static bit b; base b1, b2;
function new(int val); sub s1, s2;
a = val; othersub os1;
endfunction
virtual function void say_hi(); b1 = new(1);
$display($psprintf("hello from base (a == %0d)", a)); s1 = new(2);
endfunction os1 = new(3);
class sub extends base;
int c; s1.say_hi();
function new(int val); os1.say_hi();
super.new(val);
c = val; b2 = os1;
endfunction b2.say_hi();
virtual function void say_hi();
super.say_hi(); $display($psprintf("b == %0d", base::b));
$display($psprintf("hello from sub (c == %0d)", c)); $display($psprintf("b == %0d", othersub::b));
endfunction end
endclass endprogram

20

You might also like