ubus_tb_top.sv
興味あるところは1つだけ。initial文のところです。
initial begin
uvm_config_db#(virtual ubus_if)::set(uvm_root::get(), "*", "vif", vif);
run_test();
end
ここの、uvm_config_dbのset文です。ここでvirtual interfaceのセットをしていることはわかるのですが、この1行で何をしているのかと。
調べたら難しかったので、ubusで使用している使用例から考えていきます。
- virtual interfaceのセットは、module ubus_tb_topで行っている。このとき
uvm_config_db#(virtual ubus_if)::set(uvm_root::get(), "*", "vif", vif);
- 第一引数は、どのアクセス対象のinstance情報を渡しているようです。実行するuvm_testクラスはわからないので、こう書くのかな?
- 第二引数はインスタンス名。すべてのインスタンスを対象。
- 第三引数はフィールド名。クラスの変数(メンバ)名を指定します。
- 第四引数は、見つけたフィールドにvifを渡しています
- その他は、UVMのクラスの中でセットしており、
uvm_config_db#(int)::set(this,"ubus_example_tb0.ubus0.masters[0].sequencer.loop_read_modify_write_seq", "itr", 6);
- 第一引数は "this"、つまり自分自身を基準に、第二引数引数で具体的なインスタンス名、第三引数でフィールド、第四引数で値をセットしています。
この使い方から、virtual interfaceだけ使い方が異なることがわかります。
以下に途中まで調べた経緯を書いていますが、頓挫してしまいました。
とりあえず、適当なuvm_test classを用意して、uvm_root::get()を実行してみました。
# uvm_root::get()='{m_leaf_name:"", m_inst_id:13, use_uvm_seeding:1, m_inst_count:451, __m_uvm_status_container:@uvm_status_container@1, m_rh:@uvm_root_report_handler@1, enable_stop_interrupt:0, print_enabled:1, recorder:null, m_domain:@uvm_domain@2, m_phase_imps:'{ }, m_current_phase:@uvm_phase@6, m_phase_process:null, m_build_done:1, m_phasing_active:0, m_parent:null, m_children:'{"uvm_test_top":@test@1 }, m_children_by_handle:'{@test@1:@test@1 }, m_stream_handle:'{ }, m_tr_h:'{ }, m_name:"", event_pool:null, recording_detail:0, m_verbosity_settings:'{}, m_config_set:1, print_config_matches:0, type_name:"uvm_component", m_time_settings:'{}, clp:@uvm_cmdline_processor@1, top_levels:'{@test@1}, enable_print_topology:0, finish_on_completion:1, phase_timeout:9200000000000000, m_phase_all_done:0, m_inst:@uvm_root@1}
う…いろんなところの値を所有しているんですね。
ところで、uvm_root::という表記なので、uvm_rootはclassです。uvm_rootはどんな人かというと
class uvm_root extends uvm_component
でした。んーそうですか。追うのがたいへんそうなので置いておいて、uvm_config_dbのsetメソッドを見てみましょう。
class uvm_config_db#(type T=int) extends uvm_resource_db#(T);
いました。この中を探すと
static function void set(uvm_component cntxt,
string inst_name,
string field_name,
T value);
んー、arg0がuvm_componentなんですが、上記で述べたように、uvm_root::get()はいっぱい出てきます。ただし、あの表示は "%s" ではなくて "%p" なんです。"%p"ってなに?
あーありました。見つけました。verificationguildに。
オブジェクトの表示に使うそうです。
function uvm_root uvm_root::get();
if (m_inst == null) begin
m_inst = new();
void'(uvm_domain::get_common_domain());
m_inst.m_domain = uvm_domain::get_uvm_domain();
end
return m_inst;
endfunction
m_instは、uvm_root classでした。んーこのファイルだけではわからない…。