uvm_event的使用(soc 中rtl和uvm交互)
1 前言
在soc tb验证环境中,如果不适用VIP发送激励,一般仿真的结束是由rtl中的直接调用$finish结束,而UVM并不知道仿真是什么时候开始结束了,我们可以将仿真的结束由UVM控制,但仍需要知道结束的标志,所以急需要将仿真结束的标志传给UVM中,这里提供两种方法:
uvm_config_db (在finish的地方用set标志做替代,在UVM环境内wait_modified,然后get做标志判段);
uvm_event(通过uvm_event_pool,使得TB顶层和UVM环境内部获取到相同的event,然后顶层做带数据的trigger,环境中用wait_prtiggr_data获取trigger时带的数据);
注:这里一点一定要在TB顶层,如果在rtl内部可能会由于rtl和uvm编译不在一起导致wait_prtigger_data 不成功;
这里主要介绍第二种;
2 event 具体使用
2.1 定义一个需要传输的object
class cpu_finish_status extends uvm_object;
`uvm_object_utils(cpu_finish_status)
int status;
function new(string name = "cpu_finish_status");
super.new(name);
endfunction
endclass
2.2 在TB顶层中
uvm_event e902_finish_e;
uvm_object_sting_pool #(uvm_event) evt_pool;
cpu_finish_status cpu_finish;
initial begin
//在全局中得到一个uvm_event_pool 类型的对象句柄,在整个环境中可能会有多个地方出现,在最先执行这的地方会创建并实例化唯一的一个对象,其他地方智慧获得该句柄;
evt_pool = uvm_object_string_pool#(uvm_event)::get_global_pooL();
//将uvm_event事件e902_finish_e注册到uvm_object_string_pool中
e902_finish_e = evt_pool.get("e902_finish_e");
end
//下面trigger事件
....
cpu_finish = new("cpu_finish");
cpu_finish.status = 32'h1001;
e902_finish_e.trigger(cpu_finish);
....
2.3 在uvm_test中
cpu_finish_status cpu_finish;
uvm_object cpu_finish_tmp;
function void build_phase(uvm_phase);
...
evt_pool = uvm_object_string_pool#(uvm_event)::get_global_pooL();
e902_finish_e = evt_pool.get("e902_finish_e");
cpu_finish = new("cpu_finish");
...
endfunction
task main_phase(uvm_phase phase);
...
forever bgein
e902_finish_e.wait_trigger_data(cpu_finish_tmp);
if(!$cast(cpu_finish,cpu_finish_tmp)) begin
`uvm_error("CAST ERR","...")
end
...
end
...
endtask
浙公网安备 33010602011771号