Introduction
Introduction Get started Hello UVM example UVM Phases Part 1 UVM Phases Part 2 UVM Base Classes UVM Object and Core Methods UVM ComponentsBuilding a Testbench
UVM Transaction UVM Sequence UVM Sequencer UVM Driver UVM Monitor UVM Scoreboard UVM Agent UVM Environment UVM TestOther Components
Coverage CollectorExecution Model
UVM Phases ObjectionsCommunication
TLM Basics TLM Blocking Put Port TLM Non-Blocking Put Port TLM Blocking Peek Port Analysis Ports TLM FIFOConfiguration
UVM Factory UVM Config DBRuntime Control
UVM Plusargs Seeds & Reproducibility Verbosity Control Debug Runtime ControlsAdvanced
Virtual Sequences Virtual SequencerUVM RAL
Intro Abstraction Flexibility Comparison Coverage Minimum Requirements Learning Path Register Types First Implementation Register with 2 Fields Register with Reserved Bits Access Policies Part 1 Access Policies Part 2 Access Policies Part 3 Access Policies Part 4 Memory Modeling Register Block Adapter Introduction Adapter Methods Adapter Example Predictor Types Desired and Mirror Values Register Methods Desired Value Mirror ValueUVMArena
Introduction
Introduction Get started Hello UVM example UVM Phases Part 1 UVM Phases Part 2 UVM Base Classes UVM Object and Core Methods UVM ComponentsBuilding a Testbench
UVM Transaction UVM Sequence UVM Sequencer UVM Driver UVM Monitor UVM Scoreboard UVM Agent UVM Environment UVM TestOther Components
Coverage CollectorExecution Model
UVM Phases ObjectionsCommunication
TLM Basics TLM Blocking Put Port TLM Non-Blocking Put Port TLM Blocking Peek Port Analysis Ports TLM FIFOConfiguration
UVM Factory UVM Config DBRuntime Control
UVM Plusargs Seeds & Reproducibility Verbosity Control Debug Runtime ControlsAdvanced
Virtual Sequences Virtual SequencerUVM RAL
Intro Abstraction Flexibility Comparison Coverage Minimum Requirements Learning Path Register Types First Implementation Register with 2 Fields Register with Reserved Bits Access Policies Part 1 Access Policies Part 2 Access Policies Part 3 Access Policies Part 4 Memory Modeling Register Block Adapter Introduction Adapter Methods Adapter Example Predictor Types Desired and Mirror Values Register Methods Desired Value Mirror ValueVirtual Sequencer in UVM
A virtual sequencer is used to coordinate activity across multiple sequencers. This page explains the concept from scratch using a simple and practical example.
1. The Problem We Want to Solve
In a simple UVM environment, a sequence communicates with a single sequencer, which then sends transactions to the driver.
sequence → sequencer → driver → DUT
This works well when only one interface exists. However, real designs usually contain multiple interfaces such as memory, interrupts, configuration buses, or debug interfaces.
Each interface has its own agent and sequencer. The challenge appears when a test must coordinate activity across multiple interfaces.
2. Why a Normal Sequencer Is Not Enough
A normal sequencer controls only one driver and one interface. System-level scenarios require:
- Multiple sequencers running together
- Ordering between operations
- Synchronization between interfaces
For example:
1. Send write transaction
2. Wait for interrupt
3. Read status register
This coordination cannot be handled cleanly by a single agent sequence.
3. What Is a Virtual Sequencer?
A virtual sequencer is a central object that contains handles to multiple real sequencers.
- It does not connect to a driver
- It does not send transactions to the DUT
- It only provides access to other sequencers
Virtual Sequencer
/ \
Write Sequencer Read Sequencer
It acts as a coordinator between different interfaces.
4. Virtual Sequencer vs Virtual Sequence
Virtual Sequencer
A container that stores references to other sequencers.
class virtual_sequencer extends uvm_sequencer;
write_sequencer wr_seqr;
read_sequencer rd_seqr;
endclass
Virtual Sequence
The virtual sequence is the brain. It runs on the virtual sequencer and controls multiple sequences.
wseq.start(p_sequencer.wr_seqr);
rseq.start(p_sequencer.rd_seqr);
5. Basic Example Environment
The virtual sequencer allows one test to control both interfaces.
6. Virtual Sequencer Implementation
class virtual_sequencer extends uvm_sequencer;
`uvm_component_utils(virtual_sequencer)
write_sequencer wr_seqr;
read_sequencer rd_seqr;
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction
endclass
Notice that no driver or transaction handling exists here.
7. Connecting Sequencers in the Environment
class my_env extends uvm_env;
`uvm_component_utils(my_env)
write_agent wr_agent;
read_agent rd_agent;
virtual_sequencer vseqr;
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction
function void build_phase(uvm_phase phase);
super.build_phase(phase);
wr_agent = write_agent::type_id::create("wr_agent", this);
rd_agent = read_agent::type_id::create("rd_agent", this);
vseqr = virtual_sequencer::type_id::create("vseqr", this);
endfunction
function void connect_phase(uvm_phase phase);
vseqr.wr_seqr = wr_agent.seqr;
vseqr.rd_seqr = rd_agent.seqr;
endfunction
endclass
This step allows the virtual sequence to access both sequencers.
8. Virtual Sequence Example
class virtual_sequence extends uvm_sequence;
`uvm_object_utils(virtual_sequence)
`uvm_declare_p_sequencer(virtual_sequencer)
function new(string name = "virtual_sequence");
super.new(name);
endfunction
task body();
write_seq wseq;
read_seq rseq;
wseq = write_seq::type_id::create("wseq");
rseq = read_seq::type_id::create("rseq");
`uvm_info("VSEQ", "Starting WRITE", UVM_LOW)
wseq.start(p_sequencer.wr_seqr);
`uvm_info("VSEQ", "Starting READ", UVM_LOW)
rseq.start(p_sequencer.rd_seqr);
endtask
endclass
The virtual sequence defines the system behavior by controlling multiple sequencers.
9. Execution Flow
- The test starts the virtual sequence.
- The virtual sequence runs on the virtual sequencer.
- The virtual sequence starts sequences on real sequencers.
- Drivers execute transactions on the DUT.
Key Takeaway
- Sequencer → controls one interface
- Virtual sequencer → holds multiple sequencers
- Virtual sequence → coordinates system behavior
Complete Source Code
This page explains the architecture and concepts behind the virtual sequencer example. To explore the full SystemVerilog and UVM implementation, including environment setup, sequences, and test configuration, visit the repository below.
View on GitHub