//sequence_items
class ps_sequence_item extends uvm_sequence_item;
//randomize inputs
rand bit wx_p_t, wx_n_t, wy_p_t, wy_n_t, wz_p_t, wz_n_t;
rand bit ax_p_t , ax_n_t, ay_p_t, ay_n_t, az_p_t, az_n_t;
bit chip_sel_t, clk_buf_t, rstn_t;
bit [7:1] gpb_ad_t;
//outputs
bit [15:0] regio_t;
bit clk50_t;
function new (string name="ps_sequence_item");
super.new(name);
endfunction: new
`uvm_object_utils_begin(ps_sequence_item)
`uvm_field_int(wx_p_t,UVM_DEFAULT)
`uvm_field_int(wx_n_t,UVM_DEFAULT)
`uvm_field_int(wy_p_t,UVM_DEFAULT)
`uvm_field_int(wy_n_t,UVM_DEFAULT)
`uvm_field_int(wz_p_t,UVM_DEFAULT)
`uvm_field_int(wz_n_t,UVM_DEFAULT)
`uvm_field_int(ax_p_t,UVM_DEFAULT)
`uvm_field_int(ax_n_t,UVM_DEFAULT)
`uvm_field_int(ay_p_t,UVM_DEFAULT)
`uvm_field_int(ay_n_t,UVM_DEFAULT)
`uvm_field_int(az_p_t,UVM_DEFAULT)
`uvm_field_int(az_n_t,UVM_DEFAULT)
`uvm_field_int(chip_sel_t,UVM_DEFAULT)
`uvm_field_int(clk_buf_t,UVM_DEFAULT)
`uvm_field_int(rstn_t,UVM_DEFAULT)
`uvm_field_int(gpb_ad_t,UVM_DEFAULT)
`uvm_field_int(regio_t,UVM_DEFAULT)
`uvm_field_int(clk50_t,UVM_DEFAULT)
`uvm_object_utils_end
endclass: ps_sequence_item
class ps_sequencer extends uvm_sequencer #(ps_sequence_item);
// UVM Factory Registration
`uvm_sequencer_utils(ps_sequencer)
// Construction
function new(string name="ps_sequencer", uvm_component parent=null);
super.new(name,parent);
endfunction:new
endclass
//pulse_synch_sequence class.
class ps_sequence extends uvm_sequence #(ps_sequence_item);
`uvm_object_utils(ps_sequence)
ps_sequence_item trans;
function new (string name="ps_sequence");
super.new(name);
endfunction
virtual task body ();
forever
//begin
//repeat(2)
begin
trans = ps_sequence_item::type_id::create("trans"); //sequence item handle
start_item(trans);
assert(trans.randomize());
finish_item(trans);
end
//end
endtask: body
endclass:ps_sequence
/***************************************
*/
//pulse_synch_driver
class ps_driver extends uvm_driver #(ps_sequence_item);
//Macros
`uvm_component_utils(ps_driver)
// Virtual Interface
virtual ps_if ps_if;
//Constructor
function new (string name,uvm_component parent);
super.new(name,parent);
endfunction: new
//Build Phase
function void build_phase(uvm_phase phase);
`uvm_info(get_full_name(), "Build phase called in driver", UVM_LOW)
super.build_phase(phase);
void'(uvm_resource_db#(virtual ps_if )::read_by_name(.scope("ifs"), .name("ps_if"), .val(ps_if)));
endfunction: build_phase
//Run Phase
virtual task run_phase(uvm_phase phase);
super.run_phase(phase);
`uvm_info(get_full_name(), "Run phase called in driver", UVM_LOW)
fork
reset;
drive(phase);
join
`uvm_info(get_full_name(), "Run phase end in driver", UVM_LOW)
endtask: run_phase
//Reset The DUT Task
task reset;
uvm_report_info(get_full_name(), "Start of reset method in driver", UVM_LOW);
//wait state for reset-active low
wait(ps_if.rstn_f==0);
@(negedge ps_if.clk_buf_f)
forever
begin
ps_if.wx_p_f<=1'b0;
/*
ps_if.wx_n_f<=1'b0;
ps_if.wy_p_f<=1'b0;
ps_if.wy_n_f<=1'b0;
ps_if.wz_p_f<=1'b0;
ps_if.wz_n_f<=1'b0;
ps_if.ax_p_f<=1'b0;
ps_if.ax_n_f<=1'b0;
ps_if.ay_p_f<=1'b0;
ps_if.ay_n_f<=1'b0;
ps_if.az_p_f<=1'b0;
ps_if.az_n_f<=1'b0;
*/
ps_if.chip_sel_f<=1'b0;
ps_if.gpb_ad_f<=8'b00000000;
@(posedge ps_if.rstn_f);
end
uvm_report_info(get_full_name(),"End of reset method in driver", UVM_LOW);
endtask : reset
/*******************************************************/
//Drive Task
task drive(uvm_phase phase);
// Objects
ps_sequence_item trans;
wait (ps_if.rstn_f==1);
@(negedge ps_if.rstn_f);
@(posedge ps_if.clk_buf_f);
forever
begin
//starting transactions
seq_item_port.get_next_item(trans);
uvm_report_info(get_full_name(),"Driving packet ...",UVM_LOW);
@(posedge ps_if.clk_buf_f)
begin
if(ps_if.clk50_f==1'b1)
begin
ps_if.wx_p_f = 1'b1;
# (108*251) ps_if.wx_p_f = 1'b0;
# (108*37);
ps_if.gpb_ad_f=8'b11111111;
ps_if.chip_sel_f=1'b1;
ps_if.gpb_ad_f=8'b01000000; //0x1840
#(108*1);
ps_if.chip_sel_f=1'b0;
#(108*19);
ps_if.chip_sel_f=1'b1;
#(108*1);
ps_if.gpb_ad_f=8'b11111111;
end
end
seq_item_port.item_done ();
//ending transactions
end
endtask:drive
endclass:ps_driver
// Two monitors should be defined
// 1- to sample actual data from the DUT-Interface
// 2- to get expected data => Golden Reference Data
/*********************************************/
//pulse_synch_monitor class to get actual data from DUT-Interface
class ps_monitor extends uvm_monitor;
`uvm_component_utils(ps_monitor)
// Object of main Transaction class
ps_sequence_item trans;
//ps_coverage cov ; //ps_coverage class handle
//uvm_analysis_port for item_collection
uvm_analysis_port#(ps_sequence_item) mon_ap;
function new(string name="ps_monitor", uvm_component parent=null);
super.new(name, parent);
mon_ap = new ("mon_ap", this);
endfunction: new
//Virtual Interface
virtual ps_if ps_if;
//Build Phase
function void build_phase(uvm_phase phase);
super.build_phase(phase);
uvm_report_info(get_full_name(),"Build phase starts in monitor", UVM_LOW);
void'(uvm_resource_db#(virtual ps_if)::read_by_name(.scope("ifs"), .name("ps_if"), .val(ps_if)));
trans = ps_sequence_item::type_id::create("trans", this);
uvm_report_info(get_full_name(),"Build phase ends in monitor", UVM_LOW);
endfunction: build_phase
//Run Phase
task run_phase(uvm_phase phase);
super.run_phase(phase);
//This task monitors the interface for a complete transaction and writes to analysis port when complete
uvm_report_info(get_full_name(),"Run phase starts in monitor", UVM_LOW);
wait(ps_if.rstn_f===1);
@(negedge ps_if.rstn_f);
forever
begin
@(negedge ps_if.clk_buf_f)
begin
trans.clk50_t =ps_if.clk50_f; //output clk50
trans.regio_t =ps_if.regio_f; //output regio
end
mon_ap.write(trans); //write to analysis port after sampling the transactions from the interface
end
endtask: run_phase
endclass: ps_monitor
/****************************************************/
Simulation seems to be running continuous with following reports