[CU]uvm lab5.1-router(不推荐)
注1:uvm lab1 - __见贤思齐 - 博客园 (cnblogs.com)
注2:uvm lab2 - __见贤思齐 - 博客园 (cnblogs.com)
注3:uvm lab3 - __见贤思齐 - 博客园 (cnblogs.com)
注4:uvm lab4 - __见贤思齐 - 博客园 (cnblogs.com)
注5:uvm lab5 - __见贤思齐 - 博客园 (cnblogs.com)
学习目标
(1) uvm_seq_lib的使用;
1.test.sv
1 program automatic test; 2 import uvm_pkg::*; 3 4 `include "test_collection.sv" 5 6 initial begin 7 $timeformat(-9, 1, "ns", 10); 8 run_test(); 9 end 10 11 endprogram
2.test_collection.sv
1 `ifndef TEST_COLLECTION__SV 2 `define TEST_COLLECTION__SV 3 4 `include "router_env.sv" 5 6 class test_base extends uvm_test; 7 `uvm_component_utils(test_base) 8 9 router_env env; 10 11 function new(string name, uvm_component parent); 12 super.new(name, parent); 13 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 14 endfunction 15 16 virtual function void build_phase(uvm_phase phase); 17 super.build_phase(phase); 18 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 19 env = router_env::type_id::create("env", this); 20 uvm_config_db#(virtual router_io)::set(this, "env.i_agent[*]", "router_io", router_test_top.sigs); 21 uvm_config_db#(virtual router_io)::set(this, "env.o_agent[*]", "router_io", router_test_top.sigs); 22 uvm_config_db#(virtual router_io)::set(this, "env.r_agent", "router_io", router_test_top.sigs); 23 24 // Lab 6 - Task 5, Step 2 25 // There are three ways to register sequences into a sequence library: 26 // 27 // 1 - Use `uvm_add_to_seq_lib() macro 28 // 2 - Use the sequence library class's add_typewide_sequence() method 29 // 3 - Use the sequence library object's add_sequence() method 30 // 31 // There are different consequences with each of these mechanisms. 32 // 33 // The `uvm_add_to_seq_lib() macro will add the sequence to the sequence library for all tests. 34 // 35 // The add_typewide_sequence() method will add the sequence to the sequence library only 36 // for the test that called the method. 37 // 38 // The add_sequence() method, requires that an instance of the sequence library be constructed. 39 // Then, the add_sequence() method called via this sequence library handle will only affect 40 // the sequencer that's configured to use this particular sequence library object. 41 // 42 // For this lab, use the add_typewide_sequence() method in the test_base class to add the 43 // packet_sequence to the packet_seq_lib. 44 // 45 // ToDo 46 packet_seq_lib::add_typewide_sequence(packet_sequence::get_type()); 47 48 endfunction 49 50 virtual function void final_phase(uvm_phase phase); 51 super.final_phase(phase); 52 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 53 uvm_top.print_topology(); 54 uvm_factory::get().print(); 55 endfunction 56 endclass 57 58 `include "packet_da_3.sv" 59 60 class test_da_3_inst extends test_base; 61 `uvm_component_utils(test_da_3_inst) 62 63 function new(string name, uvm_component parent); 64 super.new(name, parent); 65 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 66 endfunction 67 68 virtual function void build_phase(uvm_phase phase); 69 super.build_phase(phase); 70 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 71 set_inst_override_by_type("env.i_agent*.seqr.*", packet::get_type(), packet_da_3::get_type()); 72 endfunction 73 endclass 74 75 class test_da_3_type extends test_base; 76 `uvm_component_utils(test_da_3_type) 77 78 function new(string name, uvm_component parent); 79 super.new(name, parent); 80 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 81 endfunction 82 83 virtual function void build_phase(uvm_phase phase); 84 super.build_phase(phase); 85 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 86 set_type_override_by_type(packet::get_type(), packet_da_3::get_type()); 87 endfunction 88 endclass 89 90 class test_da_3_seq extends test_base; 91 `uvm_component_utils(test_da_3_seq) 92 93 function new(string name, uvm_component parent); 94 super.new(name, parent); 95 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 96 endfunction 97 98 virtual function void build_phase(uvm_phase phase); 99 super.build_phase(phase); 100 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 101 uvm_config_db#(bit[15:0])::set(this, "env.i_agent*.seqr", "da_enable", 16'h0008); 102 uvm_config_db#(int)::set(this, "env.i_agent*.seqr", "item_count", 20); 103 endfunction 104 endclass 105 106 107 // Lab 6 - Task 7, Step 2 108 // Create a test class called test_seq_lib_cfg extended from test_base. 109 // 110 // Within the class, create an instance of uvm_sequence_library_cfg, call it seq_cfg. 111 // 112 // ToDo 113 class test_seq_lib_cfg extends test_base; 114 uvm_sequence_library_cfg seq_cfg; 115 `uvm_component_utils(test_seq_lib_cfg) 116 function new(string name, uvm_component parent); 117 super.new(name, parent); 118 endfunction 119 120 121 // Lab 6 - Task 7, Step 3 122 // 123 // Define a build phase in which the seq_cfg object is constructed with UVM_SEQ_LIB_RAND mode 124 // and the max_random_count and the min_random_count to 1. 125 // 126 // Then, configure all the agent sequencer's sequence library to use this configuration. 127 // 128 // ToDo 129 virtual function void build_phase(uvm_phase phase); 130 super.build_phase(phase); 131 seq_cfg = new("seq_cfg", UVM_SEQ_LIB_RAND, 1, 1); 132 uvm_config_db #(uvm_sequence_library_cfg)::set(this, "env.i_agent*.seqr.main_phase", "default_sequence.config", seq_cfg); 133 endfunction 134 endclass 135 136 137 `endif
3.router_env.sv
1 `ifndef ROUTER_ENV__SV 2 `define ROUTER_ENV__SV 3 4 `include "input_agent.sv" 5 `include "reset_agent.sv" 6 `include "output_agent.sv" 7 `include "ms_scoreboard.sv" 8 9 10 class router_env extends uvm_env; 11 input_agent i_agent[16]; 12 scoreboard sb; 13 output_agent o_agent[16]; 14 reset_agent r_agent; 15 16 17 `uvm_component_utils(router_env) 18 19 function new(string name, uvm_component parent); 20 super.new(name, parent); 21 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 22 endfunction 23 24 virtual function void build_phase(uvm_phase phase); 25 super.build_phase(phase); 26 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 27 28 foreach (i_agent[i]) begin 29 i_agent[i] = input_agent::type_id::create($sformatf("i_agent[%0d]", i), this); 30 uvm_config_db #(int)::set(this, i_agent[i].get_name(), "port_id", i); 31 32 // Lab 6 - Task 4, Step 2 33 // Replace the following configuration of the sequencers to use the sequence library 34 // (packet_seq_lib) instead of packet sequence (packet_sequence): 35 // 36 // ToDo 37 uvm_config_db #(uvm_object_wrapper)::set(this, {i_agent[i].get_name(), ".", "seqr.main_phase"}, "default_sequence", packet_seq_lib::get_type()); 38 //uvm_config_db #(uvm_object_wrapper)::set(this, {i_agent[i].get_name(),".sqr.reset_phase"}, "default_sequence", router_input_port_reset_sequence::get_type()); 39 end 40 41 sb = scoreboard::type_id::create("sb", this); 42 foreach (o_agent[i]) begin 43 o_agent[i] = output_agent::type_id::create($sformatf("o_agent[%0d]",i),this); 44 uvm_config_db #(int)::set(this, o_agent[i].get_name(), "port_id", i); 45 end 46 47 r_agent = reset_agent::type_id::create("r_agent", this); 48 uvm_config_db #(uvm_object_wrapper)::set(this, {r_agent.get_name(), ".", "seqr.reset_phase"}, "default_sequence", reset_sequence::get_type()); 49 endfunction 50 51 virtual function void connect_phase(uvm_phase phase); 52 super.connect_phase(phase); 53 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 54 foreach (i_agent[i]) begin 55 i_agent[i].analysis_port.connect(sb.before_export); 56 end 57 foreach (o_agent[i]) begin 58 o_agent[i].analysis_port.connect(sb.after_export); 59 end 60 endfunction 61 62 endclass 63 64 `endif
4.input_agent.sv
(1) 与lab5中input_agent.sv相同;
4.1driver.sv
(1) 与lab5中driver.sv相同;
4.2iMonitor.sv
(1) 与lab5中iMonitor.sv相同;
5.output_agent.sv
(1) 与lab5中output_agent.sv相同;
5.1oMonitor.sv
(1) 与lab5中oMonitor.sv相同;
6.reset_agent.sv
(1) 与lab5中reset_agent.sv相同;
7.ms_scoreboard.sv
(1) 与lab5中ms_scoreboard.sv相同;
8.packet_seq_lib_pkg.sv
1 // Lab 6 - Task 2, Step 2 2 // 3 // Declare a package called packet_seq_lib_pkg. 4 // package packet_seq_lib_pkg; 5 // 6 // ToDo 7 package packet_seq_lib_pkg; 8 9 10 // Lab 6 - Task 2, Step 3 11 // 12 // Import the uvm_pkg package. 13 // import uvm_pkg::*; 14 // 15 // ToDo 16 import uvm_pkg::*; 17 18 19 // 20 // The packet class is moved inside the package. 21 // 22 class packet extends uvm_sequence_item; 23 rand bit[3:0] sa, da; 24 rand bit[7:0] payload[$]; 25 26 `uvm_object_utils_begin(packet) 27 `uvm_field_int(sa, UVM_ALL_ON | UVM_NOCOMPARE) 28 `uvm_field_int(da, UVM_ALL_ON) 29 `uvm_field_queue_int(payload, UVM_ALL_ON) 30 `uvm_object_utils_end 31 32 constraint valid { 33 payload.size inside {[1:10]}; 34 } 35 36 function new(string name="packet"); 37 super.new(name); 38 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH) 39 endfunction 40 endclass 41 42 // Lab 6 - Task 2, Step 4 43 // 44 // Every sequencen library that you create will have the identical structure. 45 // The only thing that changes is the name of the class and the sequence item type. 46 // 47 // The uvm_sequence_library_utils macro creates the infrastructure for the sequence 48 // library class. The macro and the init_sequence_library() call are required to 49 // to be able to populate the sequence library with sequences are registered 50 // with it or any of its base classes. 51 // 52 // Create the packet sequence library as follows: 53 // 54 // class packet_seq_lib extends uvm_sequence_library #(packet); 55 // `uvm_object_utils(packet_seq_lib) 56 // `uvm_sequence_library_utils(packet_seq_lib) 57 // 58 // function new(string name = "packet_seq_lib"); 59 // super.new(name); 60 // `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 61 // init_sequence_library(); 62 // endfunction 63 // endclass 64 // 65 // ToDo 66 class packet_seq_lib extends uvm_sequence_library #(packet); 67 `uvm_object_utils(packet_seq_lib) 68 `uvm_sequence_library_utils(packet_seq_lib) 69 70 function new(string name = "packet_seq_lib"); 71 super.new(name); 72 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 73 init_sequence_library(); 74 endfunction 75 endclass 76 77 78 endpackage
8.1packet_sequence.sv
1 `ifndef PACKET_SEQUENCE__SV 2 `define PACKET_SEQUENCE__SV 3 4 // Lab 6 - Task 3, Step 2 5 // The packet class now resides inside the packet sequence library package. 6 // 7 // Replace the following include statement with an import of the packet sequence library package: 8 // import packet_seq_lib_pkg::*; 9 // 10 // ToDo 11 import packet_seq_lib_pkg::*; 12 13 14 class packet_sequence extends uvm_sequence #(packet); 15 int item_count = 10; 16 int port_id = -1; 17 bit[15:0] da_enable = '1; 18 int valid_da[$]; 19 20 `uvm_object_utils_begin(packet_sequence) 21 `uvm_field_int(item_count, UVM_ALL_ON) 22 `uvm_field_int(port_id, UVM_ALL_ON) 23 `uvm_field_int(da_enable, UVM_ALL_ON) 24 `uvm_field_queue_int(valid_da, UVM_ALL_ON) 25 `uvm_object_utils_end 26 27 function void pre_randomize(); 28 uvm_config_db#(int)::get(m_sequencer, "", "item_count", item_count); 29 uvm_config_db#(int)::get(m_sequencer, "", "port_id", port_id); 30 uvm_config_db#(bit[15:0])::get(m_sequencer, "", "da_enable", da_enable); 31 if (!(port_id inside {-1, [0:15]})) begin 32 `uvm_fatal("CFGERR", $sformatf("Illegal port_id value of %0d", port_id)); 33 end 34 35 valid_da.delete(); 36 for (int i=0; i<16; i++) 37 if (da_enable[i]) 38 valid_da.push_back(i); 39 endfunction 40 41 function new(string name = "packet_sequence"); 42 super.new(name); 43 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 44 endfunction 45 46 virtual task body(); 47 48 // Lab 6 - Task 3, Step 3 49 // Create a parent sequence handle, call it parent. 50 // 51 // uvm_sequence_base parent; 52 // 53 // ToDo 54 uvm_sequence_base parent; 55 56 57 `uvm_info("TRACE", $sformatf("%m"), UVM_HIGH); 58 uvm_config_db#(int)::get(m_sequencer, "*", "item_count", item_count); 59 60 // Lab 6 - Task 3, Step 4 and 5 61 // Call get_parent_sequence() to retrive the parent sequence handle. 62 // 63 // If parent handle is not null, set the sequence's start_phase to parent 64 // sequence's starting_phase. 65 // 66 // This is necessary, because child sequences do not have start_phase of their own. 67 // 68 // parent = get_parent_sequence(); 69 // if (parent != null) begin 70 // starting_phase = parent.starting_phase; 71 // end 72 // 73 // ToDo 74 parent = get_parent_sequence(); 75 if (parent != null) begin 76 starting_phase = parent.starting_phase; 77 end 78 79 80 if (starting_phase != null) begin 81 uvm_objection objection = starting_phase.get_objection(); 82 objection.set_drain_time(this, 1us); 83 starting_phase.raise_objection(this); 84 end 85 86 repeat(item_count) begin 87 `uvm_do_with(req, {if (port_id == -1) sa inside {[0:15]}; else sa == port_id; da inside valid_da;}); 88 end 89 90 if (starting_phase != null) begin 91 starting_phase.drop_objection(this); 92 end 93 endtask 94 95 endclass 96 97 `endif
8.2packet.sv
(1) 与lab5中packet.sv相同;
8.3packet_da_3.sv
(1) 与lab5中packet_da_3.sv相同;
9.reset相关的sequence
9.1reset_sequencer.sv
9.2router_input_port_reset_sequence.sv
10.top_reset_sequencer.sv & top_reset_sequence.sv
10.1top_reset_sequencer.sv
10.2top_reset_sequence.sv
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?