0% found this document useful (0 votes)
83 views30 pages

Module Advanced Ovm Session4 Layering Sequences Tfitzpatrick

This document discusses sequences and sequencers in OVM and UVM verification and provides examples of coordinating multiple sequences across multiple interfaces. It introduces the concept of virtual sequences and sequencers to improve reusability. Virtual sequences contain pointers to actual sequencers. The document also discusses layered protocol verification using a layering environment and agent.

Uploaded by

vjemman
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)
83 views30 pages

Module Advanced Ovm Session4 Layering Sequences Tfitzpatrick

This document discusses sequences and sequencers in OVM and UVM verification and provides examples of coordinating multiple sequences across multiple interfaces. It introduces the concept of virtual sequences and sequencers to improve reusability. Virtual sequences contain pointers to actual sequencers. The document also discusses layered protocol verification using a layering environment and agent.

Uploaded by

vjemman
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/ 30

Advanced OVM (& UVM)

Layering Sequences

Tom Fitzpatrick
Verification Technologist

[email protected]
www.verificationacademy.com
Sequences & Sequencers

• Most sequences run on sequencers


• One sequencer per agent
• Env defines default sequence
• Can be overridden via factory
• Test defines other sequences
• Sequences generate
items
• Sequencer sends to driver
Sequences & Sequencers

• Interesting tests require coordinating


multiple sequences
on multiple DUT
interfaces
Coordinating Sequences
class my_test extends ovm_test;

init_seq seq1;
exec_seq seq2;
...
task run;
seq1 = init_seq::type_id::create(“seq1”);
seq2 = exec_seq::type_id::create(“seq2”);
fork
seq1.start( env.my_agent1_h.my_sequencer_h );
seq2.start( env.my_agent2_h.my_sequencer_h );
join

global_stop_request();
Not very reusable
endtask
endclass
Virtual Sequences
class test_seq extends ovm_sequence;

init_seq seq1; No parameters; test_seq
exec_seq seq2; does not generate items
my_seqr my_sequencer1_h,my_sequencer2_h;
task body();
seq1 = init_seq::type_id::create(“seq1”);
seq2 = exec_seq::type_id::create(“seq2”);
fork
seq1.start( my_sequencer1_h );
seq2.start( my_sequencer2_h );
join
… We need to know
what these are
endtask
endclass
Virtual Sequence in a Test
class seq_test extends ovm_test;

test_seq tseq;
my_env e;

virtual task run();
tseq = test_seq::type_id::create(“testseq”);
tseq.my_sequencer1_h = e.my_agent1_h.my_sequencer_h;
tseq.my_sequencer2_h = e.my_agent2_h.my_sequencer_h;
tseq1.start();
… Fill in the details after creating tseq
global_stop_request();
endtask
endclass
Virtual Sequence in a Test
class seq_test extends ovm_test;

test_seq tseq;
my_env e;

virtual task run();
tseq = test_seq::type_id::create(“testseq”);
tseq.my_sequencer1_h = e.my_agent1_h.my_sequencer_h;
tseq.my_sequencer2_h = e.f.g.h.agent_h.seqr_h;
tseq1.start();

global_stop_request();
endtask
endclass Any compatible sequencer will do
Virtual Sequence in an Environment
class seq_env extends ovm_env;

test_seq tseq;
my_agent my_agent1_h, my_agent2_h;

virtual task run();
tseq = test_seq::type_id::create(“testseq”);
tseq.my_sequencer1_h = my_agent1_h.my_sequencer_h;
tseq.my_sequencer2_h = my_agent2_h.my_sequencer_h;
tseq1.start();
… Dependencies
global_stop_request();
endtask
endclass
What About Reuse?

• We want this:

• To look like this:

Need the virtual sequence


to run on a sequencer
What About Reuse?

• It will actually be
something like this:
Sequencer pointers in
virtual sequence point
to handles in virtual
“Virtual Sequencer” sequencer
contains pointers to the
actual sequencers
Virtual sequencer is the
“component anchor “ to
configure sequence
Virtual Sequencer
class virt_sequencer extends ovm_sequencer;
Extend base

component to add
my_seqr ctrl_seqr_h;
my_sequencer1_h; sequencer pointers
my_other_seqr my_sequencer2_h;
data_seqr_h; Use names that
indicate functionality
function new( string name ,
ovm_component parent = null );
super.new( name , parent );
endfunction
endclass
This is the easy part ☺
Setting Up the Virtual Sequence
class virt_sequence_base extends ovm_sequence;
… Hide the details in a
my_seqr ctrl_seqr_h; base sequence
my_other_seqr data_seqr_h;

virt_sequencer virt_sqr_h; Type-specific


task body(); virtual sequencer
Ensure proper
if(!$cast(virt_sqr_h, m_sequencer)) m_sequencer type
`ovm_fatal(“SeqrTypeMismatch”,
“Wrong Virtual Sequencer Type”); Set the pointers
ctrl_seqr_h = virt_sqr_h.ctrl_seqr_h;
data_seqr_h = virt_sqr_h.data_seqr_h;
endtask
endclass
The Virtual Sequence Writer Has it Easy
class test_seq extends virt_sequence_base;

init_seq seq1; Use Base Sequence
Create the child
exec_seq seq2; Infrastructure
sequences
task body();
super.body();
seq1 = init_seq::type_id::create(“seq1”);
seq2 = exec_seq::type_id::create(“seq2”);
fork Just need to know the
seq1.start( ctrl_seqr_h ); sequencer names
seq2.start( data_seqr_h );
join

endtask
endclass
Connect the Sequencers in the Environment
class seq_env extends ovm_env;

virt_sequencer vseqr;
my_agent ctrl_agent_h;
my_other_agent data_agent_h;

virtual function void connect();


vseqr.ctrl_seqr_h =
ctrl_agent_h.my_sequencer_h;
vseqr.data_seqr_h =
data_agent_h.my_sequencer_h;
endfunction
endclass
Start the Virtual Sequence Like Any Other
class seq_env extends ovm_env;

virt_sequencer vseqr;
my_agent ctrl_agent_h;
my_other_agent data_agent_h;
test_seq tseq;

virtual task run();


tseq = test_seq::type_id::create(“tseq”);
tseq.start(vseqr);
global_stop_request();
endtask
endclass
Use Test to Override Default Virtual Sequence
class vseq_test extends ovm_test;

tseq2 tseq_h;
my_env e;

function void start_of_simulation();
test_seq::type_id::
set_type_override(tseq2::get_type());
endfunction
endclass
Layered Protocols
Protocol Layering Schemes

• 1:1
• Transaction of one type converted into another
• Register -> bus
• 1:many
• High-level transaction converted to multiple low-
level
• Many:1
• Multiple higher-level transactions aggregated
• Converse happens on the response
Layering Architecture
Preserve the
Agent/Sequener
view

This connection
is the key

Ideally, without
changing the agent

Standard Agent

Convert Upper layer


to Lower layer
Layering Architecture

Look familiar?
The Layering Environment
class layer_env extends ovm_env;
… Parameterized by
lower_agent low_agent_h; upper-level req[,rsp]
ovm_layering_agent #(upper) up_agent_h; Create from Factory

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);

endfunction
endclass
The Layering Environment
class layer_env extends ovm_env;
… Parameterized by
lower_agent low_agent_h; upper-level req[,rsp]
ovm_layering_agent #(upper) up_agent_h; Create from Factory

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(

);

endfunction Must be called in build()


endclass
The Layering Environment
class layer_env extends ovm_env;

lower_agent low_agent_h;
ovm_layering_agent #(upper) up_agent_h;

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(“upper",

);
Just a name
endfunction
endclass
The Layering Environment
class layer_env extends ovm_env;

lower_agent low_agent_h;
ovm_layering_agent #(upper) up_agent_h;

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(“upper", up_sequencer::get_type(),

);
Upper Sequencer Type
endfunction created in the layering_agent
endclass
The Layering Environment
class layer_env extends ovm_env;

lower_agent low_agent_h;
ovm_layering_agent #(upper) up_agent_h;

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(“upper", up_sequencer::get_type
“Lagent",
);
Lower Agent Name
endfunction
endclass
The Layering Environment
class layer_env extends ovm_env;

lower_agent low_agent_h;
ovm_layering_agent #(upper) up_agent_h;

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(“upper", up_sequencer::get_type
“Lagent", U2L_xlseq::get_type(),
);

endfunction Translation Sequence Type


endclass Started in lower sequencer
The Layering Environment
class layer_env extends ovm_env;

lower_agent low_agent_h;
ovm_layering_agent #(upper) up_agent_h;

virtual function void build();


low_agent_h = lower_agent::type_id::create(“Lagent”,this);
up_agent_h =
ovm_layer_agent #(upper)::type_id::create(“Uagent”,this);
up_agent_h.create_mapping(“upper", up_sequencer::get_type
“Lagent", U2L_xlseq::get_type(),
upper_seq::get_type() );

endfunction Upper sequence type


endclass Started in upper sequencer
The Translation Sequence
class U2L_xlseq extends ovm_translator_base #(.REQ(upper),
.sequence_base(ovm_sequence #(lower));

task body(); Parameterized base type
upper ureq, ursp;
super.body(); Built-in seq_item_pull_port

Looks like a driver


sequencer_port.get(ureq);
req = new(); Built-in of type parameter REQ
req = u2l_xlate(ureq);
start_item(req); Translate upper to lower
finish_item(req);
get_response(rsp); Translate lower back to upper
ursp = l2u_xlate(rsp);
ursp.set_id_info(ureq); Write upper response back out
response_port.write(ursp);
endtask
endclass
Protocol Layering
Preserve the
Agent/Sequener
view

This connection
is the key

Ideally, without
changing the agent

Standard Agent

Convert Upper layer


to Lower layer
Advanced OVM (& UVM)
Layering Sequences

Tom Fitzpatrick
Verification Technologist

[email protected]
www.verificationacademy.com

You might also like