agent是保存并连接driver,monitor和sequencer实例的容器。agent基于协议或接口要求开发结构化层次结构。
uvm_agent class declaration:
virtual class uvm_agent extends uvm_component
User-defined class declaration:
class <agent_name> extends uvm_agent;
1 uvm_agent class hierarchy
2 How to create a UVM agent?
- 创建一个从 uvm_agent 扩展的用户定义agent类,并将其注册到工厂中。
- 在 build_phase 中,实例化driver,monitor和sequencer如果它是active的。如果它是passive agent,则只实例化monitor。
- 在 connect_phase 中,连接driver和sequencer组件。
3 Types of Agent
There are two types of agents
- Active agent
- Passive agent
3.1 Active Agent
active agent驱动激励给DUT,实例化三个component:driver,monitor和sequencer。
3.2 Passive Agent
passive agent不驱动激励给DUT。它只实例化monitor。它被用作覆盖率coverage采样接口和checker检查的目的。
3.3 How to configure the agent as an active or passive agent?
agent通常在UVM env环境类里例化。因此,它在env里或者其他实例化agent的component里使用配置参数 is_active对agent进行配置。
set_config_int("<path_to_agent>", "is_active", UVM_ACTIVE);
set_config_int("<path_to_agent>", "is_active", UVM_PASSIVE);
注:默认情况下,所有agent被配置为UVM_ACTIVE。
3.3.1 Code snippet to configure agent type with set_config_int
// Env Code
class env extends uvm_agent;
a_agent agt_a; // Active agent
p_agent agt_p; // Passive agent
`uvm_component_utils(env)
function new(string name = "env", uvm_component parent = null);
super.new(name, parent);
endfunction
function void build_phase(uvm_phase phase);
super.build_phase(phase);
agt_a = a_agent::type_id::create("agt_a", this);
agt_p = p_agent::type_id::create("agt_p", this);
set_config_int("agt_p", "is_active", UVM_PASSIVE); // Configure p_agent as passive agent
endfunction
endclass
Output:
UVM_WARNING /xcelium20.09/tools/methodology/UVM/CDNS-1.2/sv/src/base/uvm_component.svh(3061) @ 0: uvm_test_top.env_o [UVM/CFG/SET/DPR] get/set_config_* API has been deprecated. Use uvm_config_db instead.
UVM_INFO agent.sv(16) @ 0: uvm_test_top.env_o.agt_a [agt_a] This is Active agent
UVM_INFO agent.sv(40) @ 0: uvm_test_top.env_o.agt_p [agt_p] This is Passive agent
UVM_INFO /xcelium20.09/tools/methodology/UVM/CDNS-1.2/sv/src/base/uvm_root.svh(605) @ 0: reporter [UVMTOP] UVM testbench topology:
--------------------------------------------------------------
Name Type Size Value
--------------------------------------------------------------
uvm_test_top base_test - @1835
env_o env - @1902
agt_a a_agent - @1933
drv driver - @1996
rsp_port uvm_analysis_port - @2117
seq_item_port uvm_seq_item_pull_port - @2065
mon_A monitor_A - @2002
seqr sequencer - @2150
rsp_export uvm_analysis_export - @2210
seq_item_export uvm_seq_item_pull_imp - @2770
arbitration_queue array 0 -
lock_queue array 0 -
num_last_reqs integral 32 'd1
num_last_rsps integral 32 'd1
agt_p p_agent - @1966
mon_B monitor_B - @2860
--------------------------------------------------------------
uvm1.2已经弃用set_config_int方法了。如果你用uvm1.2运行代码,会出现下面的UVM_WARNING。
UVM_WARNING: uvm_test_top.env_o [UVM/CFG/SET/DPR] get/set_config_* API has been deprecated.
Use uvm_config_db instead.
3.3.2 Code snippet to configure agent type with uvm_config_db
// Env code
class env extends uvm_agent;
a_agent agt_a; // Active agent
p_agent agt_p; // Passive agent
`uvm_component_utils(env)
function new(string name = "env", uvm_component parent = null);
super.new(name, parent);
endfunction
function void build_phase(uvm_phase phase);
super.build_phase(phase);
agt_a = a_agent::type_id::create("agt_a", this);
agt_p = p_agent::type_id::create("agt_p", this);
uvm_config_db #(uvm_active_passive_enum)::set(this, "agt_p", "is_active", UVM_PASSIVE);
endfunction
endclass
Output:
UVM_INFO agent.sv(16) @ 0: uvm_test_top.env_o.agt_a [agt_a] This is Active agent
UVM_INFO agent.sv(40) @ 0: uvm_test_top.env_o.agt_p [agt_p] This is Passive agent
UVM_INFO /xcelium20.09/tools/methodology/UVM/CDNS-1.2/sv/src/base/uvm_root.svh(605) @ 0: reporter [UVMTOP] UVM testbench topology:
--------------------------------------------------------------
Name Type Size Value
--------------------------------------------------------------
uvm_test_top base_test - @1838
env_o env - @1905
agt_a a_agent - @1936
drv driver - @1999
rsp_port uvm_analysis_port - @2117
seq_item_port uvm_seq_item_pull_port - @2065
mon_A monitor_A - @1873
seqr sequencer - @2150
rsp_export uvm_analysis_export - @2210
seq_item_export uvm_seq_item_pull_imp - @2770
arbitration_queue array 0 -
lock_queue array 0 -
num_last_reqs integral 32 'd1
num_last_rsps integral 32 'd1
agt_p p_agent - @1969
mon_B monitor_B - @2859
--------------------------------------------------------------
3.4 How does the user-defined agent know whether it is an active or passive agent?
get_is_active()函数被用来查找agent的类型。如果是active agent,会实例化driver,sequencer。而monitor实例和agent type无关。即,monitor总是会被实例化。
get_is_active()函数会返回一个uvm_active_passive_enum类型的枚举变量UVM_ACTIVE或者UVM_PASSIVE。
3.4.1 Active Agent example
class a_agent extends uvm_agent;
driver drv;
sequencer seqr;
monitor_A mon_A;
`uvm_component_utils(a_agent)
function new(string name = "a_agent", uvm_component parent = null);
super.new(name, parent);
endfunction
function void build_phase(uvm_phase phase);
super.build_phase(phase);
if(get_is_active() == UVM_ACTIVE) begin
drv = driver::type_id::create("drv", this);
seqr = sequencer::type_id::create("seqr", this);
`uvm_info(get_name(), "This is Active agent", UVM_LOW);
end
mon_A = monitor_A::type_id::create("mon_A", this);
endfunction
function void connect_phase(uvm_phase phase);
super.connect_phase(phase);
if(get_is_active() == UVM_ACTIVE)
drv.seq_item_port.connect(seqr.seq_item_export);
endfunction
endclass
3.4.2 Passive Agent example
class p_agent extends uvm_agent;
monitor_B mon_B;
`uvm_component_utils(p_agent)
function new(string name = "p_agent", uvm_component parent = null);
super.new(name, parent);
endfunction
function void build_phase(uvm_phase phase);
super.build_phase(phase);
if(get_is_active() == UVM_PASSIVE) begin
mon_B = monitor_B::type_id::create("mon_B", this);
`uvm_info(get_name(), "This is Passive agent", UVM_LOW);
end
endfunction
endclass
4 How an agent build a structural hierarchy with various protocols?
(Agent如何使用各种协议构建结构层次结构)
根据协议接口,将激励驱动至 DUT。因此,通过为不同的协议接口设置不同的agent,提供了构建结构层次结构的灵活性。
例如:
在下图中,
- agent_ahb 特定于 AHB 接口。
- agent_axi 特定于 AXI 接口。
- agent_apb 特定于 APB 接口。