日本免费高清视频-国产福利视频导航-黄色在线播放国产-天天操天天操天天操天天操|www.shdianci.com

學無先后,達者為師

網站首頁 編程語言 正文

UVM中analysis端口的使用方法

作者:Alfred.HOO 更新時間: 2022-07-11 編程語言

UVM中有兩種特殊的端口:analysis_port和analysis_export。這兩者其實與put和get系列端口類似,都用于傳遞transaction。它們的區別是:
第一,默認情況下,一個analysis_port(analysis_export)可以連接多個IMP,也就是說,analysis_port(analysis_export)與IMP
之間的通信是一對多的通信,而put和get系列端口與相應IMP的通信是一對一的通信(除非在實例化時指定可以連接的數量,參照4.2.1節A_port的new函數原型代碼清單4-4)。analysis_port(analysis_export)更像是一個廣播。

第二,put與get系列端口都有阻塞和非阻塞的區分。但是對于analysis_port和analysis_export來說,沒有阻塞和非阻塞的概念。
因為它本身就是廣播,不必等待與其相連的其他端口的響應,所以不存在阻塞和非阻塞。一個analysis_port可以和多個IMP相連接進行通信,但是IMP的類型必須是uvm_analysis_imp,否則會報錯。
對于put系列端口,有put、try_put、can_put等操作,對于get系列端口,有get、try_get和can_get等操作。對于analysis_port和
analysis_export來說,只有一種操作:write。在analysis_imp所在的component,必須定義一個名字為write的函數。

要實現圖中所示的連接關系,A的代碼為:

文件:src/ch4/section4.3/4.3.1/analysis_port/A.sv
3 class A extends uvm_component;
4   `uvm_component_utils(A)
5
6   uvm_analysis_port#(my_transaction) A_ap; //
…
13 endclass
…
20 task A::main_phase(uvm_phase phase); //
21   my_transaction tr;
22   repeat(10) begin
23     #10;
24     tr = new("tr");
25     assert(tr.randomize());
26     A_ap.write(tr); //
27    end
28 endtask

A的代碼很簡單,只是簡單地定義一個analysis_port,并在main_phase中每隔10個時間單位寫入一個transaction。B的代碼為:

文件:src/ch4/section4.3/4.3.1/analysis_port/B.sv
3 class B extends uvm_component;
4 `uvm_component_utils(B)
5
6 uvm_analysis_imp#(my_transaction, B) B_imp; //
…
15 endclass
…
26 function void B::write(my_transaction tr); //
27   `uvm_info("B", "receive a transaction", UVM_LOW)
28   tr.print();
29 endfunction

如前所述,B是B_imp所在的component,因此要在B中定義一個名字為write的函數。在B的main_phase中不需要做任何操作。
C的代碼與B完全相似,只要把相應的B替換為C即可。
env中的連接關系為:

//my_env.sv
29 function void my_env::connect_phase(uvm_phase phase);
30 super.connect_phase(phase);
31 A_inst.A_ap.connect(B_inst.B_imp);
32 A_inst.A_ap.connect(C_inst.C_imp);
33 endfunction

上面只是一個analysis_port與IMP相連的例子。analysis_export和IMP也可以這樣相連接,只需將上面例子中的
uvm_analysis_port改為uvm_analysis_export就可以。
與put系列端口的PORT和EXPORT直接相連會出錯的情況一樣,analysis_port如果和一個analysis_export直接相連也會出錯。只
有在analysis_export后面再連接一級uvm_analysis_imp,才不會出錯。

現實情況中,scoreboard除了接收monitor的數據之外,還要接收reference model的數據。相應的scoreboard就要再添加一個
uvm_analysis_imp的IMP,如model_imp。此時問題就出現了,由于接收到的兩路數據應該做不同的處理,所以這個新的IMP也要
有一個write任務與其對應。但是write只有一個,怎么辦?
UVM考慮到了這種情況,它定義了一個宏uvm_analysis_imp_decl來解決這個問題,其使用方式為:

//my_scoreboard.sv
4 `uvm_analysis_imp_decl(_monitor) //
5 `uvm_analysis_imp_decl(_model)   //
6 class my_scoreboard extends uvm_scoreboard;
7 my_transaction expect_queue[$];
8
9 uvm_analysis_imp_monitor#(my_transaction, my_scoreboard) monitor_imp; //
10 uvm_analysis_imp_model#(my_transaction, my_scoreboard) model_imp;    //
…
15 extern function void write_monitor(my_transaction tr); //
16 extern function void write_model(my_transaction tr);   //
17 extern virtual task main_phase(uvm_phase phase);
18 endclass

上述代碼通過宏uvm_analysis_imp_decl聲明了兩個后綴_monitor和_model。UVM會根據這兩個后綴定義兩個新的IMP類:
uvm_analysis_imp_monitor和uvm_analysis_imp_model,并在my_scoreboard中分別實例化這兩個類:monitor_imp和model_imp。當與monitor_imp相連接的analysis_port執行write函數時,會自動調用write_monitor函數,而與model_imp相連接的analysis_port執行write函數時,會自動調用write_model函數。所以,只要完成后綴的聲明,并在write后面添加上相應的后綴就可以正常工作了:

//my_scoreboard.sv
30 function void my_scoreboard::write_model(my_transaction tr);  //
31 expect_queue.push_back(tr);
32 endfunction
33
34 function void my_scoreboard::write_monitor(my_transaction tr); //
35 my_transaction tmp_tran;
36 bit result;
37 if(expect_queue.size() > 0) begin
…
55 end
56
57 endfunction

原文鏈接:https://blog.csdn.net/Michael177/article/details/125710968

欄目分類
最近更新