比较提交

...

没有共同的提交。'master' 和 'main' 的历史完全不同。
master ... main

共有 10 个文件被更改,包括 910 次插入2 次删除
  1. +0
    -2
      README.md
  2. +11
    -0
      axi_coverage.sv
  3. +460
    -0
      axi_driver.sv
  4. +73
    -0
      axi_env.sv
  5. 二进制
      axi_incrmental.img.png
  6. +65
    -0
      axi_intrfc.sv
  7. +123
    -0
      axi_scoreboard.sv
  8. +61
    -0
      axi_seq.sv
  9. +93
    -0
      axi_seq_item.sv
  10. +24
    -0
      top.sv

+ 0
- 2
README.md 查看文件

@@ -1,2 +0,0 @@
# charan_axi_code


+ 11
- 0
axi_coverage.sv 查看文件

@@ -0,0 +1,11 @@
class axi_coverage extends uvm_subscriber#(sequence_item);
`uvm_component_utils(axi_coverage);
axi_seq_item txn;
covergroup axi_cvrg;
@(posedge clk)
coverpoint awlen{ bins b1[]={[1,3,7,15]};}
coverpoint awsize{ bins b2[]={[1:7]};}
coverpoint awburst{ bins b3[]={0,1,2};
ignore_bins b31={3};}
endgroup

+ 460
- 0
axi_driver.sv 查看文件

@@ -0,0 +1,460 @@
class driver extends uvm_driver #(seq);
`uvm_component_utils(driver)
virtual axi_driver_if vif;
sequence seq;
function new(string name="driver", uvm_component parent=null);
super.new(name, parent);
endfunction
virtual function void build_phase(uvm_phase phase);
super.build_phase(phase);
seq=sequence::type_id::create("seq");
if(!uvm_config_db#(virtual axi_driver_if)::get(this," ","vif",vif))
`uvm_error("driver"," Interface not set");
endfunction
task reset();
begin
vif.awvalid <= 0;
vif.awready <= 0;
vif.awid <= 0;
vif.awlen <= 0;
vif.awsize <= 0;
vif.awaddr <= 0;
vif.awburst <= 0;
vif.wvalid <= 0;
vif.wready <= 0;
vif.wid <= 0;
vif.wdata <= 0;
vif.wstrb <= 0;
vif.wlast <= 0;
vif.bready <= 0;
vif.bvalid <= 0;
vif.bid <= 0;
vif.bresp <= 0;
vif.arvalid <= 0;
vif.arready <= 0;
vif.arid <= 0;
vif.arlen <= 0;
vif.arsize <= 0;
vif.araddr <= 0;
vif.arburst <= 0;
vif.rvalid <= 0;
vif.rready <= 0;
vif.rid <= 0;
vif.rdata <= 0;
vif.rstrb <= 0;
vif.rlast <= 0;
vif.rresp <= 0;
@(posedge vif.clk);
`uvm_info(get_type_name(),"reset applied",UVM_MEDIUM)
end
endtask
virtual task run_phase(uvm_phase phase);
reset();
seq_tem_port.get_next_item(txn);
if(wr_rd==1)
begin
wrtie_address();
write_data();
write_response();
end
else
begin
read_address();
read_data();
end
endtask
virtual task write_address();
vif.awready<=0;
vif.awaddr<= txn.awaddr;
vif.awsize<= txn.awsize;
vif.awlen<= txn.awlen;
vif.awcache<= txn.awcache;
vif.awburst<= txn.awburst;
vif.awvalid<=1'b1;
case (txn.awburst)
2'b00 : write_ad_fixed_burst;
2'b01 : write_ad_incr_burst;
2'b10 : write_ad_wrap_burst;
endcase
while(vif.awready==0)
$display("within loop");
begin
@(posedge vif.clk);
if(vif.awvalid==1)
begin
awready=1;
$display("write address phase is completed");
end
end
vif.awvalid=0;
endtask
////////////////// wridte_fixed burst////////////////
virtual task write_ad_fixed_burst();
vif.awlen <= txn.awlen;
vif.awid <= txn.awid;
vif.awaddr <= txn.awaddr;
vif.awsize<= txn.awsize;
vif.awvalid<= 1;
wait(vif.awready);
vif.awvalid<=0;
write_data();
endtask
virtual task write_data();
vif.wready<=0;
for(int i=0;i<=txn.awlen+1;i++) begin
$display("write data started");
vif.wdata<=txn.wdata[i];
vif.wstrb<=txn.wstrb[i];
vif.wid<=txn.wid;
vif.wvalid<=1'b1;
if(i=txn.awlen+1) vif.wlast=1;
while (wready=0)
begin @(posedge vif.clk)
if (vif.wready==1)
txn.wready=1;
end
vif.wlast=0;
vif.wvalid=0;
vif.wready=0;
$display("write data completed");
end
write_ad_incr();
endtask
//////////////////////write_address_incremental/////////////////
virtual task write_ad_incr();
vif.awlen <= txn.awlen;
for(int i=0; i<(txn.awlen +1);i++)
vif.awid <= txn.awid;
vif.awaddr <= txn.awaddr;
vif.awsize<= txn.awsize;
txn.awaddr<= txn.awaddr+(2**awsize);
vif.awvalid<= 1;
wait(vif.awready);
vif.awvalid<=0;
write_data();
endtask
virtual task write_data();
vif.wready<=0;
for(int i=0;i<=txn.awlen+1;i++) begin
$display("write data started");
vif.wdata<=txn.wdata[i];
vif.wstrb<=txn.wstrb[i];
vif.wid<=txn.wid;
vif.wvalid<=1'b1;
if(i=txn.awlen+1) vif.wlast=1;
while (wready=0)
begin @(posedge vif.clk)
if (vif.wready==1)
txn.wready=1;
end
vif.wlast=0;
vif.wvalid=0;
vif.wready=0;
$display("write data completed");
write_ad_wrap();
end
endtask
///////////wri_address_wrap///////////////////////
virtual task write_ad_wrap();
vif.awlen <= '{1,3,7,15};
vif.awid <= txn.awid;
vif.awaddr <= txn.awaddr;
vif.awsize<= txn.awsize;
begin
int burst_length=(awlen+1);
int burst_size=(awsize+1);
int lower_boundary=INT[awaddr/(burst_length*burst_size)]*(burst_length*burst_size);
int upper_boundary=lower_boundar+(burst_length*burst_size);
for (int i=0; i< (pkt.awlen+1);i++)
begin
if(vif.awaddr==upper_boundary)
vif.awaddr=lower_boundary;
else
vif.awaddr <= vif.awaddr+ (2**vif.awsize);
vif.awvalid<= 1;
wait(vif.awready);
vif.awvalid<=0;
end
write_data();
endtask
virtual task write_data();
vif.wready<=0;
for(int i=0;i<=txn.awlen+1;i++) begin
$display("write data started");
vif.wdata<=txn.wdata[i];
vif.wstrb<=txn.wstrb[i];
vif.wid<=txn.wid;
vif.wvalid<=1'b1;
if(i=txn.awlen+1) vif.wlast=1;
while (wready=0)
begin @(posedge vif.clk)
if (vif.wready==1)
txn.wready=1;
end
vif.wlast=0;
vif.wvalid=0;
vif.wready=0;
$display("write data completed");
write_response();
end
endtask
virtual task write_response();
if(vif.wvalid&&vif.wready&&vif.wlast)
wait(bvalid)
begin
vif.bid = pkt.bid;
vif.bresp = pkt.bresp;
end
vif.bready <= 1 ;
for(i=0;i<=awlen+1;i++)
begin
if(vif.awid==vif.bid)
case(vif.bresp)
2'b00:"okay";
2'b01:"exclusive okay";
2'b10:"slave error";
2'b11:"decode error";
endcase
end
vif.bready<=0;
endtask
///////////////////////Read address////////////////////////////////////////////////
task read_adress();
`uvm_info("master_driver",$sformatf("message from driver\n %s",pkt.sprint()),UVM_HIGH)
vif.arid <= pkt.arid;
vif.araddr <= pkt.araddr;
vif.arlen <= pkt.arlen;
vif.arsize <= pkt.arsize;
vif.arburst <= pkt.arburst;
vif.arvalid <= 1;
`uvm_info("master_driver",$sformatf("message from driver \n %s",pkt.sprint()),UVM_HIGH)
case (txn.arburst)
2'b00 : read_address_fixed_burst;
2'b01 : read_address_incr_burst;
2'b10 : read_address_wrap_burst;
endcase
@(posedge vif.clk);
wait (vif.arready);
vif.arvalid <= 0;
endtask
//////////////////////////////////////// raed wrap burst////////////////////
virtual task read_ad_wrap();
vif.awlen <= '{1,3,7,15};
vif.arid <= txn.arid;
vif.araddr <= txn.araddr;
vif.arsize<= txn.arsize;
begin
int burst_length=(arlen+1);
int burst_size=(arsize+1);
int lower_boundary=INT[araddr/(burst_length*burst_size)]*(burst_length*burst_size);
int upper_boundary=lower_boundar+(burst_length*burst_size);
for (int i=0; i< (txn.arlen+1);i++)
begin
if(vif.araddr==upper_boundary)
vif.araddr=lower_boundary;
else
vif.araddr <= vif.araddr+ (2**vif.arsize);
vif.arvalid<= 1;
wait(vif.arready);
vif.arvalid<=0;
end
read_data1();
endtask
virtual task read_data1();
vif.rready<=0;
for(int i=0;i<=txn.arlen+1;i++) begin
$display("read data started");
vif.rdata<=txn.rdata[i];
vif.rid<=txn.rid;
vif.rvalid<=1'b1;
if(i=txn.arlen+1) vif.rlast=1;
while (rready=0)
begin @(posedge vif.clk)
if (vif.rready==1)
txn.rready=1;
end
vif.rlast=0;
vif.rvalid=0;
$display("read data completed");
end
foreach (vif.rdata[i])
begin
if (vif.arid == vif.rid)
begin
case (vif.rresp)
2'b00 : s = "Transaction OKAY";
2'b01 : s = "Transaction FAILED";
2'b10 : s = "SLAVE ERROR";
2'b11 : s = "DEEOCDE ERROR";
endcase
`uvm_info("axi master_driver",$sformatf("\n t %s response for the received data \n",s),UVM_MEDIUM)
end
end
vif.rready <= 0;
endtask
//////////////////////////////////////// INCR address ////////////////
task read_address_incr_burst();
vif.arlen <=txn.arlen;
for(int i=0; i<(arlen +1);i++)
begin
vif.araddr<=txn.araddr;
vif.arid <= txn.arid;
vif.arvalid<= 1;
txn.araddr<= txn.araddr +(2**vif.arsize);
wait(vif.arready);
vif.arvalid<=0;
end
read_data();
endtask
virtual task read_data();
vif.rready<=0;
for(int i=0;i<=txn.arlen+1;i++) begin
$display("read data started");
vif.rdata<=txn.rdata[i];
vif.rid<=txn.rid;
vif.rvalid<=1'b1;
if(i=txn.arlen+1) vif.rlast=1;
while (rready=0)
begin @(posedge vif.clk)
if (vif.rready==1)
txn.rready=1;
end
vif.rlast=0;
vif.rvalid=0;
$display("read data completed");
end
vif.rready <= 1;
foreach (vif.rdata[i])
begin
if (vif.arid == vif.rid)
begin
case (vif.rresp)
2'b00 : s = "Transaction OKAY";
2'b01 : s = "Transaction FAILED";
2'b10 : s = "SLAVE ERROR";
2'b11 : s = "DEEOCDE ERROR";
endcase
`uvm_info("master_driver",$sformatf("\n\t %s response for the recieved data \n",s),UVM_MEDIUM)
end
end
vif.rready <= 0;
endtask
///////////////read address fixed burst////////////////////////
task read_address_fixed_burst ();
begin
vif.arlen <= txn.arlen;
vif.arid <= txn.arid;
vif.araddr <= txn.araddr;
vif.arvalid<= 1;
wait(vif.arready);
vif.arvalid<=0;
end
rd_dt_fixed_burst();
endtask
task rd_dt_fixed_burst ();
vif.rready<=0;
for(int i=0;i<=txn.arlen+1;i++) begin
$display("read data started");
vif.rdata<=txn.rdata[i];
vif.rid<=txn.rid;
vif.rvalid<=1'b1;
if(i=txn.arlen+1) vif.rlast=1;
while (rready=0)
begin @(posedge vif.clk)
if (vif.rready==1)
txn.rready=1;
end
vif.rlast=0;
vif.rvalid=0;
$display("read data completed");
end
foreach (vif.rdata[i])
begin
if (vif.arid == vif.rid)
begin
case (vif.rresp)
2'b00 : s = "Transaction OKAY";
2'b01 : s = "Transaction FAILED";
2'b10 : s = "SLAVE ERROR";
2'b11 : s = "DEEOCDE ERROR";
endcase
`uvm_info("master_driver",$sformatf("\n\t %s response for recieved data \n",s),UVM_MEDIUM)
end
end
vif.rready <= 0;
endtask
if(txn.reset==1) begin
reset();
end
//Write operation support
else if(txn.wr_rd==1) begin
`uvm_info(get_type_name()," write packet is received in driver ",UVM_MEDIUM)
begin
write_address();
end
//read operation support
else if( txn.wr_rd==0)
begin
read_address();
end
seq_item_port.item_done();
end
endtask
endclass

+ 73
- 0
axi_env.sv 查看文件

@@ -0,0 +1,73 @@
class axi_env extends uvm_env;

axi_env_config env_cfg_h;
master_agent_top mst_agt_top;
slave_agent_top slv_agt_top;
virtual_sequencer vseqr_h;
scoreboard sb;

extern function new(string name="axi_env",uvm_component parent);
extern function void build_phase(uvm_phase phase);
extern function void connect_phase(uvm_phase phase);
`uvm_component_utils(axi_env)
endclass

function axi_env::new(string name="axi_env",uvm_component parent);
super.new(name,parent);
endfunction

function void axi_env::build_phase(uvm_phase phase);
if(!uvm_config_db#(axi_env_config)::get(this,"","axi_env_config",env_cfg_h))
`uvm_fatal("AXI Env","Unable to get axi env config, have you set it in test?")
if(env_cfg_h.has_master_agent)
begin
uvm_config_db#(master_config)::set(this,"mst_agt_top*","master_config",env_cfg_h.mst_cfg_h);
mst_agt_top=master_agent_top::type_id::create("mst_agt_top",this);
end

if(env_cfg_h.has_slave_agent)
begin
uvm_config_db#(slave_config)::set(this,"slv_agt_top*","slave_config",env_cfg_h.slv_cfg_h);
slv_agt_top=slave_agent_top::type_id::create("slv_agt_top",this);
end

if(env_cfg_h.has_virtual_sequencer)
begin
vseqr_h=virtual_sequencer::type_id::create("vseqr_h",this);
end
if(env_cfg_h.has_scoreboard)
sb=scoreboard::type_id::create("sb",this);

super.build_phase(phase);

endfunction

function void axi_env::connect_phase(uvm_phase phase);
if(env_cfg_h.has_virtual_sequencer)
begin
if(env_cfg_h.has_master_agent)
begin
foreach(mst_agt_top.mst_agt_h[i])
vseqr_h.mst_seqr_h[i]=mst_agt_top.mst_agt_h[i].mst_seqr_h;
end

if(env_cfg_h.has_slave_agent)
begin
foreach(slv_agt_top.slv_agt_h[i])
vseqr_h.slv_seqr_h[i]=slv_agt_top.slv_agt_h[i].slv_seqr_h;
end
end
if(env_cfg_h.has_scoreboard)
begin
foreach(mst_agt_top.mst_agt_h[i])
mst_agt_top.mst_agt_h[i].mst_mon_h.mst_mon_port.connect(sb.mst_fifo_h[i].analysis_export);
foreach(slv_agt_top.slv_agt_h[i])
slv_agt_top.slv_agt_h[i].slv_mon_h.slv_mon_port.connect(sb.slv_fifo_h[i].analysis_export);
end
endfunction



二进制
axi_incrmental.img.png 查看文件

之前 之后
宽度: 1920  |  高度: 1080  |  大小: 438 KiB

+ 65
- 0
axi_intrfc.sv 查看文件

@@ -0,0 +1,65 @@
Interfate axi_intf(input bit clk, reset);
///////////////////write address channel/////////////
input logic awvalid;
output logic awready; input logic [3:0] awid;
input logic [3:0] awlen;
input logic [2:0] awsize;
input logic [31:0] awaddr;
input logic [1:0] awburst;
/////////////////////write data channel//////////////////////////
input logic wvalid;
output logic wready;
input logic [3:0] wid;
input logic [31:0] wdata;
input logic [3:0] wstrb;
input logic wlast;
///////////////write response channel/////////////////////
input logic bready;
output logic bvalid;
output logic [3:0] bid;
output logic [1:0] bresp;
////////////// read address channel////////////////
output logic reg arready;
input logic [3:0] arid;
input logic [31:0] araddr;
input logic [3:0] arlen;
input logic [2:0] arsize;
input logic [1:0] arburst;
input logic arvalid;
///////////////////read data channel////////////////////
output logic [3:0] rid;
output logic [31:0]rdata;
output logic [1:0] rresp;
output logic rlast;
output logic rvalid;
input logic rready;
////////////////////bvalid assertion//////////////
property wvalid_wready;
@(posedge clk) (wvalid && wready)|=> bvalid;
endproperty
assert property(wvalid_wready)
$display("bvalid is asserted after wvalid and wready:assertion passed");
else
'uvm_error("assertion failed");
////////////////////rvalid assertion//////////////
property arvalid_arready;
@(posedge clk) (arvalid && arready)|=> rvalid;
endproperty
assert property(arvalid_arready)
$display("rvalid is asserted after arvalid and arready:assertion passed");
else
'uvm_error("assertion failed");
endinterface

+ 123
- 0
axi_scoreboard.sv 查看文件

@@ -0,0 +1,123 @@
class scoreboard extends uvm_scoreboard;
`uvm_component_utils(scoreboard)

uvm_tlm_analysis_fifo#(axi_xtn) mst_fifo_h[];
uvm_tlm_analysis_fifo#(axi_xtn) slv_fifo_h[];

axi_env_config env_cfg_h;
axi_xtn wr_xtn,rd_xtn;
axi_xtn mst_xtn,slv_xtn;
static int pkt_rcvd,pkt_cmprd;
covergroup write_cg;
option.per_instance=1;
awaddr_cp: coverpoint wr_xtn.AWADDR{bins awaddr_bin={[0:'hffff_ffff]};}
awburst_cp: coverpoint wr_xtn.AWBURST{bins awburst_bin[]={[0:2]};}
awsize_cp : coverpoint wr_xtn.AWSIZE{bins awsize_bin[]={[0:2]};}
awlen_cp : coverpoint wr_xtn.AWLEN{bins awlen_bin={[0:11]};}
bresp_cp : coverpoint wr_xtn.BRESP{bins bresp_bin={0};}
WRITE_ADDR_CROSS: cross awburst_cp,awsize_cp,awlen_cp;
endgroup
covergroup write_cg1 with function sample(int i);
option.per_instance=1;
wdata_cp : coverpoint wr_xtn.WDATA[i]{bins wdata_bin={[0:'hffff_ffff]};}
wstrb_cp : coverpoint wr_xtn.WSTRB[i]{bins wstrobe_bin0={4'b1111};
bins wstrobe_bin1={4'b1100};
bins wstrobe_bin2={4'b0011};
bins wstrobe_bin3={4'b1000};
bins wstrobe_bin4={4'b0100};
bins wstrobe_bin5={4'b0010};
bins wstrobe_bin6={4'b0001};
bins wstrobe_bin7={4'b1110};
}
WRITE_DATA_CROSS: cross wdata_cp,wstrb_cp;
endgroup
covergroup read_cg;
option.per_instance=1;
araddr_cp: coverpoint rd_xtn.ARADDR{bins araddr_bin={[0:'hffff_ffff]};}
arburst_cp: coverpoint rd_xtn.ARBURST{bins arburst_bin[]={[0:2]};}
arsize_cp : coverpoint rd_xtn.ARSIZE{bins arsize_bin[]={[0:2]};}
arlen_cp : coverpoint rd_xtn.ARLEN{bins arlen_bin={[0:11]};}
READ_ADDR_CROSS: cross arburst_cp,arsize_cp,arlen_cp;
endgroup
covergroup read_cg1 with function sample(int i);
option.per_instance=1;
rdata_cp : coverpoint rd_xtn.RDATA[i]{bins rdata_bin={[0:'hffff_ffff]};}
rresp_cp : coverpoint rd_xtn.RRESP[i]{bins rresp_bin={0};}
endgroup
extern function new(string name="scoreboard",uvm_component parent);
extern function void build_phase(uvm_phase phase);
extern task run_phase(uvm_phase);
extern function void report_phase(uvm_phase phase);
endclass

function scoreboard::new(string name="scoreboard",uvm_component parent);
super.new(name,parent);
write_cg=new();
write_cg1=new();
read_cg=new();
read_cg1=new();
endfunction

function void scoreboard::build_phase(uvm_phase phase);
if(!uvm_config_db #(axi_env_config)::get(this,"","axi_env_config",env_cfg_h))
`uvm_fatal("Scoreboard","cannot get env config, have you set it?");

mst_fifo_h=new[env_cfg_h.no_of_master];
slv_fifo_h=new[env_cfg_h.no_of_slave];

foreach(mst_fifo_h[i])
mst_fifo_h[i]=new($sformatf("mst_fifo_h[%0d]",i),this);

foreach(slv_fifo_h[i])
slv_fifo_h[i]=new($sformatf("slv_fifo_h[%0d]",i),this);
super.build_phase(phase);
endfunction
task scoreboard::run_phase(uvm_phase phase);
forever
begin
mst_fifo_h[0].get(mst_xtn);
slv_fifo_h[0].get(slv_xtn);
pkt_rcvd++;
if(mst_xtn.compare(slv_xtn))
begin
wr_xtn=mst_xtn;
rd_xtn=mst_xtn;
pkt_cmprd++;
write_cg.sample();
read_cg.sample();
if(mst_xtn.WVALID)
begin
foreach(mst_xtn.WDATA[i])
begin
write_cg1.sample(i);
end
end
if(mst_xtn.RVALID)
begin
foreach(mst_xtn.RDATA[i])
begin
read_cg1.sample(i);
end
end
end
else
`uvm_error("Scoreboard","Master and Slave Packet Mismatch");
end
endtask


function void scoreboard::report_phase(uvm_phase phase);
`uvm_info("SCOREBOARD",$sformatf("No. of packets received:%0d",pkt_rcvd),UVM_LOW);
`uvm_info("SCOREBOARD",$sformatf("No. of packets compared:%0d",pkt_cmprd),UVM_LOW);
endfunction



+ 61
- 0
axi_seq.sv 查看文件

@@ -0,0 +1,61 @@
class write_sequence_fixed extends uvm_sequence#(axi_seq_item);
`uvm_object_utils(write_sequence)
axi_seq_item txn;
function new(string name = "write_sequence");
super.new(name);
endfunction
virtual task body();
`uvm_info(get_type_name(), $sformatf("//---------------- FIXED SEQUENCE is started -----------------//"), UVM_MEDIUM)
txn = axi_seq_item::type_id::create("txn");
start_item(txn);
assert(txn.randomize() with {awburst=2'b00;awlen=3;awsize=4};} );//FIXED
txn.wr_rd=1;
finish_item(txn);
endtask
endclass
class write_sequence_incremental extends uvm_sequence#(axi_seq_item);
`uvm_object_utils(write_sequence)
axi_seq_item txn;
function new(string name = "write_sequence");
super.new(name);
endfunction
virtual task body();
`uvm_info(get_type_name(), $sformatf("//---------------- INCREMENTAL SEQUENCE is started -----------------//"), UVM_MEDIUM)
txn = axi_seq_item::type_id::create("txn");
start_item(txn);
assert(txn.randomize() with {awburst=2'b10;awaddr==awaddr+2**awsize};} );//INCREMENTAL
txn.wr_rd=1;
finish_item(txn);
endtask
endclass
class write_sequence_wrap extends uvm_sequence#(axi_seq_item);
`uvm_object_utils(write_sequence)
axi_seq_item txn;
function new(string name = "write_sequence");
super.new(name);
endfunction
virtual task body();
`uvm_info(get_type_name(), $sformatf("//---------------- WRAP SEQUENCE is started -----------------//"), UVM_MEDIUM)
txn = axi_seq_item::type_id::create("txn");
start_item(txn);
assert(txn.randomize() with {awburst=2'b10;awlen=3;awsize=4};} );//WRAP
txn.write=1;
finish_item(txn);
endtask
endclass
class write_sequence extends uvm_sequence#(axi_seq_item);
`uvm_object_utils(write_sequence)
axi_seq_item txn;
function new(string name = "write_sequence");
super.new(name);
endfunction
virtual task body();
`uvm_info(get_type_name(), $sformatf("//---------------- WRITE SEQUENCE is started -----------------//"), UVM_MEDIUM)
txn = axi_seq_item::type_id::create("txn");
start_item(txn);
assert(txn.randomize() with {foreach(awlen[i]) if(i==awlen+1) wlast==1};} );//for last transfer
txn.wr_rd=1;
finish_item(txn);
endtask
endclass

+ 93
- 0
axi_seq_item.sv 查看文件

@@ -0,0 +1,93 @@
[Yesterday 10:04 am] Mandla Ravali
class axi_seq_item extends uvm_sequence_item;
//factory registration for object
'uvm_object_utils(axi_seq_item);
//////write address channel///////////////
bit wr_rd;
bit reset;
randc logic [31:0] awaddr;
rand logic [3:0] awlen;
rand logic [2:0] awsize;
rand logic [1:0] awburst;
rand logic [1:0] awlock;
rand logic [3:0] awcache;
bit awvalid;
bit awready;
bit [1:0] awlock;
rand logic [2:0] awprot;
bit [3:0] awid;
/////////write data channel//////////////
bit [3:0] wid;
bit [2:0] wstrb[];
logic [7:0] wdata[];
bit [1:0] bresp
bit wvalid;
bit wready;
bit wlast;
bit wstrb;
//////read address channel /////////////////
bit [3:0] arid;
randc logic [31:0] araddr;
rand logic [2:0] arsize;
rand logic [1:0] arburst;
rand logic [3:0] arlen;
rand logic [2:0] arprot;
rand logic [1:0] arlock;
rand logic [3:0] arcache;
bit arvalid;
bit arready;
///////////read data channel////////////
bit [3:0] rid;
logic [7:0] rdata;
bit rresp;
bit rvalid;
bit rready;
bit rlast;
function new (input string name = "axi_seq_item");
super.new(name);
endfunction
////4kb boundary///////////////////
constraint awaddr_4k{ awaddr % 4096 <= {(awaddr+(awsize*awlen) % 4096;}
constraint araddr_4k{ araddr % 4096 <= {(araddr+(arsize*arlen) % 4096;}
////last two bits of aligned address should be zero//////////
constraint ali_w_addr{ awaddr[1:0]==0;}
constraint ali_r_addr{ araddr[1:0]==0;}
//constraint burst_type{ awburst==2'b01;arburst==2'b01;}// burst type INCR
//////id's shoud be same for read and write////////////
constraint wr_id{ wid==awid;}
constraint rd_id{ rid==arid;}
constraint rd_rid{rid inside {[wid,awid];}}
//constraint wr_id{ wid inside{[awid]};}
//constraint rd_id{ rid inside{[arid]};}
//////increment burst////////////////////////
constraint wr_data_size{if(awburst==2'b01)
(wdata inside{[1:((2**awsize)*16)]});}
constraint rd_data_size{if(arburst==2'b01)
(rdata inside{[1:((2**arsize)*16)]});}
///// data for wrap burst///////////////////////////////////
constraint awdata{ if(awburst==2'b10)
wdata inside {((2**awsize)*2),((2**awsize)*4),((2**awsize)*8),((2**awsize)*16)};}
constraint ardata{ if(arburst==2'b10)
wdata inside {((2**arsize)*2),((2**arsize)*4),((2**arsize)*8),((2**arsize)*16)};}
endclass

+ 24
- 0
top.sv 查看文件

@@ -0,0 +1,24 @@
`include "axi_test_pkg.sv"
`include "axi_interface.sv"
module top;

import uvm_pkg::*;

import axi_test_pkg::*;

bit clk;

always #5 clk= ~clk;

axi_if axi_if0(clk);

initial
begin
uvm_config_db #(virtual axi_if)::set(null,"*","axi_if",axi_if0);
run_test("wrap_seq_test");

end

endmodule


正在加载...
取消
保存