| Автор | SHA1 | Сообщение | Дата |
|---|---|---|---|
|
|
153c9e5bd9 | Upload files to '' | 1 год назад |
|
|
716aeb11e7 | Upload files to '' | 1 год назад |
|
|
baa3b0623b | Upload files to '' | 1 год назад |
|
|
0026f1eff8 | Upload files to '' | 1 год назад |
|
|
5a53b1d5f0 | mounika | 1 год назад |
|
|
298d690d4d | mounika | 1 год назад |
|
|
139158f62f | mounika | 1 год назад |
|
|
f64b3b6482 | mounika | 1 год назад |
|
|
21c59b9753 | seq | 1 год назад |
|
|
9792b9ae88 | mounika_drv | 1 год назад |
|
|
131dc046f8 | my file1 | 1 год назад |
|
|
7d8de06b5f | test | 1 год назад |
|
|
bbe98830bd | apple file | 1 год назад |
| @@ -0,0 +1,35 @@ | |||||
| module ass(); | |||||
| //wvalid id high and wready is low then wdata,wid,wstb should be stable | |||||
| property p1(); | |||||
| @(posedge clk) | |||||
| disable iff(rst) | |||||
| (wvalid & !wready) |-> ($stable(wdata) && $stable(wid) && $stable(wstrb)); | |||||
| endproperty | |||||
| assert property (p1) | |||||
| $display("PASS"); | |||||
| else | |||||
| $diplay("FAIL"); | |||||
| //In write transaction when burst type is wrap then len must have 2,4,8 or 16 | |||||
| property p1(); | |||||
| @(posedge clk) | |||||
| disable iff(rst) | |||||
| (awvalid & awburst==2'b01) |-> ((awlen==8'b00000010)||(awlen==8`b00000100)||(awlen==8'b00001000)||(awlen==8`b00010000)); | |||||
| endproperty | |||||
| assert property (p1) | |||||
| $display("PASS"); | |||||
| else | |||||
| $diplay("FAIL"); | |||||
| endmodule | |||||
| @@ -0,0 +1,152 @@ | |||||
| class axi_drv extends uvm_driver#(axi_seq_item) | |||||
| `uvm_components_utils(axi_drv) | |||||
| virtual intf vif; | |||||
| axi_seq_item txn; | |||||
| int [31:0] temp[]; | |||||
| function new(string name="axi_drv",uvm_component parent); | |||||
| super.new(name.parent); | |||||
| endfunction | |||||
| function void build_phase(uvm_phase phase); | |||||
| uvm_config_db#(virtual intf)::get(this,"",vif,vif); | |||||
| txn=axi_seq_item::type_id::create(txn); | |||||
| endfunction | |||||
| task run_phase(uvm_phase phase); | |||||
| begin | |||||
| get_next_item(txn); | |||||
| drive(txn); | |||||
| item_done(); | |||||
| endtask | |||||
| task drive(txn); | |||||
| fork | |||||
| // reset(); | |||||
| write_add(txn); | |||||
| write_data(txn); | |||||
| read_add(txn); | |||||
| join | |||||
| endtask | |||||
| ///////////////write addr/////////// | |||||
| task write_add(txn); | |||||
| int lower_wrap_boundary; | |||||
| int upper_wrap_boundary; | |||||
| int burst_len,burst_size; | |||||
| int total_trans; | |||||
| if(txn.write==1) | |||||
| begin | |||||
| @(vif.clk); | |||||
| vif.awid<=txn.awid; | |||||
| vif.awlen<=txn.awlen; | |||||
| vif.awsize<=txn.awsize; | |||||
| vif.awburst<=txn.awburst; | |||||
| /////////fixed burst///////////// | |||||
| if(txn.awburst==2'b00) | |||||
| begin | |||||
| vif.awaddr<=txn.awaddr; | |||||
| end | |||||
| /////////////incr burst////////////// | |||||
| else if(txn.awaddr==2'b01) | |||||
| begin | |||||
| vif.awaddr<=txn.awaddr; | |||||
| for(int i=0;i<awlen;i++) | |||||
| begin | |||||
| vif.awaddr<=txn.awaddr+(2**awsize); | |||||
| end | |||||
| end | |||||
| //////////////////////wrap burst////////// | |||||
| else if(txn.awaddr==2'b10) | |||||
| begin | |||||
| if(awaddr%(2**awsize==0)) | |||||
| begin | |||||
| burst_len=awlen+1; | |||||
| burst_size=2**awsize; | |||||
| total_trans=burst_len*burst_size; | |||||
| lower_wrap_boundary=int'(awaddr/total_trans)*total_trans; | |||||
| upper_wrap_boundary=lower_wrap_boundary+total_trans; | |||||
| end | |||||
| end | |||||
| vif.awvalid<=1; | |||||
| wait(vif.awready); | |||||
| @(vif.clk); | |||||
| vif.awvalid<=0; | |||||
| end | |||||
| endtask | |||||
| //////////////write data/////////////// | |||||
| task write_data(txn); | |||||
| begin | |||||
| temp=new[txn.awlen+1]; | |||||
| forech(txn.wdata[i][j]) | |||||
| begin | |||||
| temp[i][8*j+:8]=data[i][j]; | |||||
| end | |||||
| for(i=0;i<awlen+1;i++) | |||||
| begin | |||||
| @(vif.clk); | |||||
| vif.wid<=txn.wid; | |||||
| vif.wdata<=temp[i]; | |||||
| vif.wlast<=(awlen==i)?1:0; | |||||
| end | |||||
| vif.wvalid<=1; | |||||
| wait(vif.wready) | |||||
| @(vif.clk); | |||||
| vif.wvalid<=0; | |||||
| end | |||||
| endtask | |||||
| ///////////read addr/////////// | |||||
| task read_add(txn); | |||||
| begin | |||||
| if(!txn.write) | |||||
| begin | |||||
| @(vif.clk); | |||||
| vif.arid<=txn.arid; | |||||
| vif.araddr<=txn.araddr; | |||||
| vif.arlen<=txn.arlen; | |||||
| vif.arsize<=txn.arsize; | |||||
| vif.arburst<=txn.arburst; | |||||
| vif.arvalid<=1; | |||||
| wait(vif.arready); | |||||
| @(vif.clk); | |||||
| vif.arvalid<=0; | |||||
| end | |||||
| end | |||||
| endtask | |||||
| endclass | |||||
| @@ -0,0 +1,111 @@ | |||||
| interface axi_intf #(parameter A_WIDTH = 16, D_WIDTH = 16)(input bit clk, bit rstn); | |||||
| // Write Address | |||||
| logic [8:0] AWID; | |||||
| logic [A_WIDTH-1:0] AWADDR; | |||||
| logic [3:0] AWLEN; | |||||
| logic [2:0] AWSIZE; | |||||
| logic [1:0] AWBURST; | |||||
| logic AWVALID, AWREADY; | |||||
| logic WRITE; | |||||
| // Write Data | |||||
| logic [8:0] WID; | |||||
| logic [D_WIDTH-1:0] WDATA; | |||||
| logic [(D_WIDTH/8)-1:0] WSTRB; | |||||
| logic WLAST, WVALID, WREADY; | |||||
| // Write Response | |||||
| logic [8:0] BID; | |||||
| logic [1:0] BRESP; | |||||
| logic BVALID, BREADY; | |||||
| // Read Address | |||||
| logic [8:0] ARID; | |||||
| logic [A_WIDTH-1:0] ARADDR; | |||||
| logic [3:0] ARLEN; | |||||
| logic [2:0] ARSIZE; | |||||
| logic [1:0] ARBURST; | |||||
| logic ARVALID, ARREADY; | |||||
| // Read Data | |||||
| logic [8:0] RID; | |||||
| logic [D_WIDTH-1:0] RDATA; | |||||
| logic [1:0] RRESP; | |||||
| logic RLAST, RVALID, RREADY; | |||||
| /* Clocking Blocks: 3 CBs are defined as follows | |||||
| 1. m_drv_cb - Clocking block for master driver | |||||
| 2. s_drv_cb - Clocking block for slave driver | |||||
| 3. mon_cb - Clocking block for monitors of both master and slave */ | |||||
| clocking m_drv_cb @(posedge clk); | |||||
| output AWID, AWADDR, AWLEN, AWSIZE, AWBURST,AWVALID, WID, WDATA, WSTRB, WLAST, WVALID, | |||||
| BREADY, ARID, ARADDR, ARLEN, ARSIZE, ARBURST, ARVALID, RREADY,WRITE; | |||||
| input AWREADY, WREADY, BID, BRESP, BVALID, ARREADY, RID, RDATA, RRESP, RLAST, RVALID; | |||||
| endclocking | |||||
| clocking mon_cb @(posedge clk); | |||||
| input AWID, AWADDR, AWLEN, AWSIZE, AWBURST,AWVALID, WID, WDATA, WSTRB, WLAST, WVALID, | |||||
| BREADY, ARID, ARADDR, ARLEN, ARSIZE, ARBURST, ARVALID, RREADY,WRITE; | |||||
| input AWREADY, WREADY, BID, BRESP, BVALID, ARREADY, RID, RDATA, RRESP, RLAST, RVALID; | |||||
| endclocking | |||||
| clocking s_drv_cb @(posedge clk); | |||||
| input AWID, AWADDR, AWLEN, AWSIZE, AWBURST,AWVALID, WID, WDATA, WSTRB, WLAST, WVALID, | |||||
| BREADY, ARID, ARADDR, ARLEN, ARSIZE, ARBURST, ARVALID, RREADY,WRITE; | |||||
| output AWREADY, WREADY, BID, BRESP, BVALID, ARREADY, RID, RDATA, RRESP, RLAST, RVALID; | |||||
| endclocking | |||||
| modport MDRV(clocking m_drv_cb, input rstn); | |||||
| modport MMON(clocking mon_cb, input rstn); | |||||
| modport SDRV(clocking s_drv_cb, input rstn); | |||||
| modport SMON(clocking mon_cb, input rstn); | |||||
| // ************************************************************************************************* | |||||
| // Assertions | |||||
| // ************************************************************************************************* | |||||
| // Property to check whether all write address channel remains stable after AWVALID is asserted | |||||
| property aw_valid; | |||||
| @(posedge clk) $rose(AWVALID) |-> ( $stable(AWID) | |||||
| &&$stable(AWADDR) | |||||
| &&$stable(AWLEN) | |||||
| &&$stable(AWSIZE) | |||||
| &&$stable(AWBURST)) throughout AWREADY[->1]; | |||||
| endproperty | |||||
| // Property to check whether all write address channel remains stable after AWVALID is asserted | |||||
| property w_valid; | |||||
| @(posedge clk) $rose(WVALID) |-> ( $stable(WID) | |||||
| && $stable(WDATA) | |||||
| && $stable(WSTRB) | |||||
| && $stable(WLAST)) throughout WREADY[->1]; | |||||
| endproperty | |||||
| // Property to check whether all write address channel remains stable after AWVALID is asserted | |||||
| property b_valid; | |||||
| @(posedge clk) $rose(BVALID) |-> ( $stable(BID) | |||||
| && $stable(BRESP)) throughout BREADY[->1]; | |||||
| endproperty | |||||
| // Property to check whether all write address channel remains stable after AWVALID is asserted | |||||
| property ar_valid; | |||||
| @(posedge clk) $rose(ARVALID) |-> ( $stable(ARID) | |||||
| &&$stable(ARADDR) | |||||
| &&$stable(ARLEN) | |||||
| &&$stable(ARSIZE) | |||||
| &&$stable(ARBURST)) throughout ARREADY[->1]; | |||||
| endproperty | |||||
| // Property to check whether all write address channel remains stable after AWVALID is asserted | |||||
| property r_valid; | |||||
| @(posedge clk) $rose(RVALID) |-> ( $stable(RID) | |||||
| && $stable(RDATA) | |||||
| && $stable(RRESP) | |||||
| && $stable(RLAST)) throughout RREADY[->1]; | |||||
| endproperty | |||||
| // assert property (aw_valid); | |||||
| // assert property (w_valid); | |||||
| //assert property (b_valid); | |||||
| // assert property (ar_valid); | |||||
| // assert property (r_valid); | |||||
| endinterface //axi_intf | |||||
| @@ -0,0 +1,108 @@ | |||||
| class axi_m_monitor extends uvm_monitor; | |||||
| `uvm_component_utils(axi_m_monitor) | |||||
| // Components | |||||
| uvm_analysis_port#(axi_transaction#(D_WIDTH, A_WIDTH)) ap; | |||||
| virtual axi_intf#(.D_WIDTH(D_WIDTH), .A_WIDTH(A_WIDTH)).SMON vif; | |||||
| // variables | |||||
| axi_transaction#(D_WIDTH, A_WIDTH) w_trans, r_trans; | |||||
| bit w_done, r_done; | |||||
| int b_size; | |||||
| // Methods | |||||
| extern task run_mon(uvm_phase phase); | |||||
| extern task write_monitor(); | |||||
| extern task read_monitor(); | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| w_done = 1; | |||||
| r_done = 1; | |||||
| endfunction //new() | |||||
| // Function: build_phase | |||||
| extern function void build_phase(uvm_phase phase); | |||||
| // Function: run_phase | |||||
| extern task run_phase(uvm_phase phase); | |||||
| endclass //axi_m_monitor extends uvm_monitor | |||||
| function void axi_m_monitor::build_phase(uvm_phase phase); | |||||
| ap = new("ap", this); | |||||
| endfunction: build_phase | |||||
| task axi_m_monitor::run_phase(uvm_phase phase); | |||||
| forever begin | |||||
| run_mon(phase); | |||||
| @(vif.mon_cb); | |||||
| end | |||||
| endtask: run_phase | |||||
| task axi_m_monitor::run_mon(uvm_phase phase); | |||||
| fork | |||||
| if(w_done) begin | |||||
| phase.raise_objection(this); | |||||
| w_done = 0; | |||||
| write_monitor(); | |||||
| w_done = 1; | |||||
| phase.drop_objection(this); | |||||
| end | |||||
| if(r_done) begin | |||||
| phase.raise_objection(this); | |||||
| r_done = 0; | |||||
| read_monitor(); | |||||
| r_done = 1; | |||||
| phase.drop_objection(this); | |||||
| end | |||||
| join_none | |||||
| endtask: run_mon | |||||
| task axi_m_monitor::write_monitor(); | |||||
| if(vif.mon_cb.AWVALID && vif.mon_cb.AWREADY) begin | |||||
| w_trans = axi_transaction#(D_WIDTH, A_WIDTH)::type_id::create("w_trans"); | |||||
| w_trans.addr = vif.mon_cb.AWADDR; | |||||
| w_trans.id = vif.mon_cb.AWID; | |||||
| w_trans.b_size = vif.mon_cb.AWSIZE; | |||||
| w_trans.b_len = vif.mon_cb.AWLEN; | |||||
| w_trans.b_type = B_TYPE'(vif.mon_cb.AWBURST); | |||||
| w_trans.data = new [w_trans.b_len+1]; | |||||
| for (int i=0; i<w_trans.b_len+1; i++) begin | |||||
| @(vif.mon_cb); | |||||
| wait(vif.mon_cb.WVALID && vif.mon_cb.WREADY); | |||||
| w_trans.data[i] = new [D_WIDTH/8]; | |||||
| for (int j=0; j<D_WIDTH/8; j++) begin | |||||
| w_trans.data[i][j] = vif.mon_cb.WDATA[8*j+:8]; | |||||
| end | |||||
| end | |||||
| wait(vif.mon_cb.BVALID); | |||||
| w_trans.b_resp = vif.mon_cb.BRESP; | |||||
| ap.write(w_trans); | |||||
| `uvm_info("MMON", $sformatf("WTRANS %s", w_trans.convert2string()), UVM_HIGH) | |||||
| end | |||||
| endtask: write_monitor | |||||
| task axi_m_monitor::read_monitor(); | |||||
| if(vif.mon_cb.ARVALID && vif.mon_cb.ARREADY) begin | |||||
| r_trans = axi_transaction#(D_WIDTH, A_WIDTH)::type_id::create("r_trans"); | |||||
| r_trans.addr = vif.mon_cb.ARADDR; | |||||
| r_trans.id = vif.mon_cb.ARID; | |||||
| r_trans.b_size = vif.mon_cb.ARSIZE; | |||||
| r_trans.b_len = vif.mon_cb.ARLEN; | |||||
| r_trans.b_type = B_TYPE'(vif.mon_cb.ARBURST); | |||||
| r_trans.data = new [r_trans.b_len+1]; | |||||
| r_trans.r_resp = new [r_trans.b_len+1]; | |||||
| for (int i=0; i<r_trans.b_len+1; i++) begin | |||||
| @(vif.mon_cb); | |||||
| wait(vif.mon_cb.RVALID && vif.mon_cb.RREADY); | |||||
| r_trans.data[i] = new [D_WIDTH/8]; | |||||
| for (int j=0; j<D_WIDTH/8; j++) begin | |||||
| r_trans.data[i][j] = vif.mon_cb.RDATA[8*j+:8]; | |||||
| end | |||||
| r_trans.r_resp[i] = vif.mon_cb.RRESP; | |||||
| end | |||||
| ap.write(r_trans); | |||||
| `uvm_info("MMON", $sformatf("RTRANS %s", r_trans.convert2string()), UVM_HIGH) | |||||
| end | |||||
| endtask: read_monitor | |||||
| @@ -0,0 +1,117 @@ | |||||
| //write sequence | |||||
| class axi_wr_seq extends uvm_sequence #(axi_seq_item); | |||||
| `uvm_object_utils(axi_wr_seq) | |||||
| seq_item txn; | |||||
| function new(string name="axi_wr_seq"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| task body(); | |||||
| txn=seq_item::type_id::create(txn); | |||||
| start_item(txn); | |||||
| assert(txn.randomize() with {txn.write==1;txn.awaddr==0x04;txn.wdata==0x2b1a;}); | |||||
| finish_item(txn); | |||||
| endtask | |||||
| endclass | |||||
| //read sequence | |||||
| class axi_rd_seq extends uvm_sequence #axi_(seq_item); | |||||
| `uvm_object_utils(axi_rd_seq) | |||||
| seq_item txn; | |||||
| function new(string name="axi_rd_seq"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| task body(); | |||||
| txn=seq_item::type_id::create(txn); | |||||
| start_item(txn); | |||||
| assert(txn.randomize() with {txn.write==0;txn.araddr==0x04;}); | |||||
| finish_item(txn); | |||||
| endtask | |||||
| endclass | |||||
| //unaligned sequence | |||||
| class axi_rd_seq extends uvm_sequence #(axi_seq_item); | |||||
| `uvm_object_utils(axi_rd_seq) | |||||
| seq_item txn; | |||||
| function new(string name="axi_rd_seq"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| task body(); | |||||
| txn=seq_item::type_id::create(txn); | |||||
| // if(txn.awaddr%2**awsize!=0) | |||||
| // begin | |||||
| txn.aligned_addr.constraint_mode(0); | |||||
| // end | |||||
| start_item(txn); | |||||
| assert(txn.randomize() with {txn.write==1;txn.awaddr==0x07;txn.awsize==3;}); | |||||
| finish_item(txn); | |||||
| endtask | |||||
| endclass | |||||
| //locked access sequence | |||||
| class axi_locked_access_seq extends uvm_sequence #(axi_seq_item); | |||||
| `uvm_object_utils(axi_locked_acess_seq) | |||||
| seq_item txn; | |||||
| function new(string name="axi_locked_access_seq"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| task body(); | |||||
| begin | |||||
| txn=seq_item::type_id::create(txn); | |||||
| start_item(txn); | |||||
| assert(txn.randomize() with {txn.write==1;txn.awaddr==0x04;txn.awlock==2'b10;txn.awid==01;}); | |||||
| finish_item(txn); | |||||
| end | |||||
| begin | |||||
| txn=seq_item::type_id::create(txn); | |||||
| start_item(txn); | |||||
| assert(txn.randomize() with {txn.write==1;txn.awaddr==0x04;txn.awlock==2'b10;txn.awid==02;}); | |||||
| finish_item(txn); | |||||
| end | |||||
| endtask | |||||
| endclass | |||||
| //write read sequence | |||||
| class axi_rd_seq extends uvm_sequence #(axi_seq_item); | |||||
| `uvm_object_utils(axi_rd_seq) | |||||
| seq_item txn; | |||||
| axi_wr_seq wr_seq; | |||||
| axi_rd_seq rd_seq; | |||||
| function new(string name="axi_rd_seq"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| task body(); | |||||
| begin | |||||
| txn=seq_item::type_id::create(txn); | |||||
| `uvm_do(wr_seq); | |||||
| `uvm_do(rd_seq); | |||||
| end | |||||
| endtask | |||||
| endclass | |||||
| @@ -0,0 +1,9 @@ | |||||
| class axi_seqr extends uvm_sequencer #(seq_item); | |||||
| `uvm_component_utils(axi_seqr) | |||||
| function new(string name="axi_seqr",uvm_component parent); | |||||
| super.new(name,parent); | |||||
| endfunction | |||||
| endclass | |||||
| @@ -0,0 +1,42 @@ | |||||
| //`include "uvm_pkg.sv" | |||||
| import uvm_pkg::*; | |||||
| `include "uvm_macros.svh" | |||||
| `include "axi_config_objs.svh" | |||||
| `include "axi_interface.sv" | |||||
| `include "axi_transaction.sv" | |||||
| `include "axi_write_seq.sv" | |||||
| `include "axi_read_seq.sv" | |||||
| `include "axi_m_driver.sv" | |||||
| `include "axi_m_monitor.sv" | |||||
| `include "axi_master_agent.sv" | |||||
| `include "axi_s_driver.sv" | |||||
| `include "axi_s_monitor.sv" | |||||
| `include "axi_slave_agent.sv" | |||||
| `include "axi_scoreboard.sv" | |||||
| `include "axi_env.sv" | |||||
| `include "axi_test.sv" | |||||
| `include "uvm_pkg.sv" | |||||
| // parameter A_WIDTH = 8; // Address bus width | |||||
| // parameter D_WIDTH = 128; // Data bus width | |||||
| module top; | |||||
| bit clk, rstn; | |||||
| always #5 clk = ~clk; | |||||
| initial rstn = 1; | |||||
| axi_intf#(.A_WIDTH(A_WIDTH), .D_WIDTH(D_WIDTH)) intf(clk, rstn); | |||||
| env_config env_cfg; | |||||
| initial begin | |||||
| env_cfg = new(); | |||||
| env_cfg.intf = intf; | |||||
| uvm_config_db#(env_config)::set(null, "uvm_test_top", "config", env_cfg); | |||||
| uvm_config_db#(env_config)::set(null, "uvm_test_top.env.master", "config", env_cfg); | |||||
| uvm_config_db#(env_config)::set(null, "uvm_test_top.env.slave", "config", env_cfg); | |||||
| run_test("axi_base_test"); | |||||
| end | |||||
| endmodule | |||||
| @@ -0,0 +1,166 @@ | |||||
| class axi_base_test extends uvm_test; | |||||
| `uvm_component_utils(axi_base_test) | |||||
| // Components | |||||
| axi_env env; | |||||
| axi_write_seq#(.D_WIDTH(D_WIDTH), .A_WIDTH(A_WIDTH)) wr_seq; | |||||
| axi_read_seq#(.D_WIDTH(D_WIDTH), .A_WIDTH(A_WIDTH)) rd_seq; | |||||
| // variables | |||||
| env_config env_cfg; | |||||
| test_config test_cfg; | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| test_cfg = new("test_cfg"); | |||||
| test_cfg.no_write_cases = 1; | |||||
| test_cfg.no_read_cases = 1; | |||||
| endfunction //new() | |||||
| // Function: build_phase | |||||
| extern function void build_phase(uvm_phase phase); | |||||
| // Function: end_of_elaboration_phase | |||||
| extern function void end_of_elaboration_phase(uvm_phase phase); | |||||
| // Function: run_phase | |||||
| extern task run_phase(uvm_phase phase); | |||||
| endclass //axi_base_test extends uvm_test | |||||
| function void axi_base_test::build_phase(uvm_phase phase); | |||||
| test_cfg.burst_type = 1; | |||||
| uvm_config_db#(test_config)::set(null, "uvm_test_top.seq", "config", test_cfg); | |||||
| wr_seq = new("wr_seq"); | |||||
| rd_seq = new("rd_seq"); | |||||
| env = axi_env::type_id::create("env", this); | |||||
| endfunction: build_phase | |||||
| function void axi_base_test::end_of_elaboration_phase(uvm_phase phase); | |||||
| super.end_of_elaboration_phase(phase); | |||||
| uvm_top.print_topology(); | |||||
| endfunction: end_of_elaboration_phase | |||||
| task axi_base_test::run_phase(uvm_phase phase); | |||||
| phase.raise_objection(this); | |||||
| fork | |||||
| wr_seq.start(env.master.w_seqr); | |||||
| #200 | |||||
| rd_seq.start(env.master.r_seqr); | |||||
| // end | |||||
| join | |||||
| phase.drop_objection(this); | |||||
| endtask: run_phase | |||||
| // **************************************************************************************** | |||||
| // Directed Test Cases | |||||
| // **************************************************************************************** | |||||
| class axi_write_test extends axi_base_test; | |||||
| `uvm_component_utils(axi_write_test) | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| endfunction //new() | |||||
| function void build_phase(uvm_phase phase); | |||||
| super.build_phase(phase); | |||||
| endfunction: build_phase | |||||
| function void end_of_elaboration_phase(uvm_phase phase); | |||||
| super.end_of_elaboration_phase(phase); | |||||
| endfunction: end_of_elaboration_phase | |||||
| task run_phase(uvm_phase phase); | |||||
| phase.raise_objection(this); | |||||
| wr_seq.start(env.master.w_seqr); | |||||
| phase.drop_objection(this); | |||||
| endtask: run_phase | |||||
| endclass //write_test extends axi_base_test | |||||
| class axi_read_test extends axi_base_test; | |||||
| `uvm_component_utils(axi_read_test) | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| endfunction //new() | |||||
| function void build_phase(uvm_phase phase); | |||||
| super.build_phase(phase); | |||||
| endfunction: build_phase | |||||
| function void end_of_elaboration_phase(uvm_phase phase); | |||||
| super.end_of_elaboration_phase(phase); | |||||
| endfunction: end_of_elaboration_phase | |||||
| task run_phase(uvm_phase phase); | |||||
| phase.raise_objection(this); | |||||
| wr_seq.start(env.master.w_seqr); | |||||
| // rd_seq.start(env.master.r_seqr); | |||||
| phase.drop_objection(this); | |||||
| endtask: run_phase | |||||
| endclass //write_test extends axi_base_test | |||||
| class axi_fixed_test extends axi_base_test; | |||||
| `uvm_component_utils(axi_fixed_test) | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| endfunction //new() | |||||
| function void build_phase(uvm_phase phase); | |||||
| test_cfg.burst_type = 0; | |||||
| uvm_config_db#(test_config)::set(null, "uvm_test_top.seq", "config", test_cfg); | |||||
| wr_seq = new("wr_seq"); | |||||
| rd_seq = new("rd_seq"); | |||||
| env = axi_env::type_id::create("env", this); | |||||
| endfunction: build_phase | |||||
| task run_phase(uvm_phase phase); | |||||
| super.run_phase(phase); | |||||
| endtask: run_phase | |||||
| endclass //axi_fixed_test extends axi_base_test | |||||
| class axi_incr_test extends axi_base_test; | |||||
| `uvm_component_utils(axi_incr_test) | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| endfunction //new() | |||||
| function void build_phase(uvm_phase phase); | |||||
| test_cfg.burst_type = 2; | |||||
| uvm_config_db#(test_config)::set(null, "uvm_test_top.seq", "config", test_cfg); | |||||
| wr_seq = new("wr_seq"); | |||||
| rd_seq = new("rd_seq"); | |||||
| env = axi_env::type_id::create("env", this); | |||||
| endfunction: build_phase | |||||
| task run_phase(uvm_phase phase); | |||||
| super.run_phase(phase); | |||||
| endtask: run_phase | |||||
| endclass //axi_fixed_test extends axi_base_test | |||||
| class axi_wrap_test extends axi_base_test; | |||||
| `uvm_component_utils(axi_wrap_test) | |||||
| function new(string name, uvm_component parent); | |||||
| super.new(name, parent); | |||||
| endfunction //new() | |||||
| function void build_phase(uvm_phase phase); | |||||
| test_cfg.burst_type = 2; | |||||
| uvm_config_db#(test_config)::set(null, "uvm_test_top.seq", "config", test_cfg); | |||||
| wr_seq = new("wr_seq"); | |||||
| rd_seq = new("rd_seq"); | |||||
| env = axi_env::type_id::create("env", this); | |||||
| endfunction: build_phase | |||||
| task run_phase(uvm_phase phase); | |||||
| super.run_phase(phase); | |||||
| endtask: run_phase | |||||
| endclass //axi_fixed_test extends axi_base_test | |||||
| @@ -0,0 +1,114 @@ | |||||
| `include "uvm_macros.svh" | |||||
| import uvm_pkg::*; | |||||
| class axi_seq_item extends uvm_sequence_item; | |||||
| //`uvm_object_utils(axi_seq_item) | |||||
| function new(string name="axi_seq_item"); | |||||
| super.new(name); | |||||
| endfunction | |||||
| //write address signals | |||||
| rand bit write; | |||||
| rand logic [31:0] awaddr; | |||||
| rand bit [3:0] awid; | |||||
| rand logic [3:0] awlen; | |||||
| rand logic [2:0] awsize; | |||||
| rand logic [1:0] awburst; | |||||
| rand logic [1:0] awlock; | |||||
| //write data signals | |||||
| rand bit [3:0] wid; | |||||
| rand logic [31:0] wdata[][]; | |||||
| logic [3:0] wstrb; | |||||
| logic wlast; | |||||
| //write response signals | |||||
| rand bit [3:0] Bid; | |||||
| logic [1:0] Bresp; | |||||
| //read address signals | |||||
| rand logic [31:0] araddr; | |||||
| rand bit [3:0] arid; | |||||
| rand logic [3:0] arlen; | |||||
| rand logic [2:0] arsize; | |||||
| rand logic [1:0] arburst; | |||||
| rand logic [1:0] arlock; | |||||
| //read data signals | |||||
| rand bit [3:0] rid; | |||||
| rand logic [31:0] rdata[][]; | |||||
| logic [3:0] rresp; | |||||
| rand logic rlast; | |||||
| `uvm_object_utils_begin(axi_seq_item) | |||||
| `uvm_field_int(awid,UVM_ALL_ON) | |||||
| `uvm_field_int(awaddr,UVM_ALL_ON) | |||||
| `uvm_field_int(awsize,UVM_ALL_ON) | |||||
| `uvm_field_int(awlen,UVM_ALL_ON) | |||||
| `uvm_field_int(awburst,UVM_ALL_ON) | |||||
| `uvm_field_int(awlock,UVM_ALL_ON) | |||||
| `uvm_field_int(awvalid,UVM_ALL_ON) | |||||
| `uvm_field_int(awready,UVM_ALL_ON) | |||||
| `uvm_field_int(wid,UVM_ALL_ON) | |||||
| `uvm_field_int(wdata,UVM_ALL_ON) | |||||
| `uvm_field_int(wlast,UVM_ALL_ON) | |||||
| `uvm_field_int(wstrb,UVM_ALL_ON) | |||||
| `uvm_field_int(wvalid,UVM_ALL_ON) | |||||
| `uvm_field_int(wready,UVM_ALL_ON) | |||||
| `uvm_field_int(Bid,UVM_ALL_ON) | |||||
| `uvm_field_int(Bresp,UVM_ALL_ON) | |||||
| `uvm_field_int(Bvalid,UVM_ALL_ON) | |||||
| `uvm_field_int(Bready,UVM_ALL_ON) | |||||
| `uvm_field_int(arid,UVM_ALL_ON) | |||||
| `uvm_field_int(araddr,UVM_ALL_ON) | |||||
| `uvm_field_int(arsize,UVM_ALL_ON) | |||||
| `uvm_field_int(arlen,UVM_ALL_ON) | |||||
| `uvm_field_int(arsize,UVM_ALL_ON) | |||||
| `uvm_field_int(arburst,UVM_ALL_ON) | |||||
| `uvm_field_int(arlock,UVM_ALL_ON) | |||||
| `uvm_field_int(arvalid,UVM_ALL_ON) | |||||
| `uvm_field_int(arready,UVM_ALL_ON) | |||||
| `uvm_field_int(rid,UVM_ALL_ON) | |||||
| `uvm_field_int(rdata,UVM_ALL_ON) | |||||
| `uvm_field_int(rlast,UVM_ALL_ON) | |||||
| `uvm_field_int(rresp,UVM_ALL_ON) | |||||
| `uvm_field_int(rvalid,UVM_ALL_ON) | |||||
| `uvm_field_int(rready,UVM_ALL_ON) | |||||
| `uvm_object_utils_end | |||||
| //constraints for axi | |||||
| //axi 4kb boundary | |||||
| constraint axi_4kb {awaddr%4096+(2**awsize*(awlen+1))<=4096;} | |||||
| //constarint for exclusive access | |||||
| constraint exclusive_access { | |||||
| if(awlock==2'b01) | |||||
| awlen inside{1,3,7,15};} | |||||
| // aligned addr | |||||
| constraint aligned_addr {awaddr%2**awsize==0;} | |||||
| //wrap addr | |||||
| constraint wrap_addr { | |||||
| if(awburst==2'b 10) | |||||
| awlen inside{1,3,7,15};} | |||||
| //id's should be same | |||||
| constraint wid_awid {awid==wid;} | |||||
| //id's should be same | |||||
| constraint rid_awid {arid==rid;} | |||||
| endclass | |||||