EDA Playground lets you type in and run HDL code (using a selection of free and commercial simulators and synthesizers).
It's great for learning HDLs, it's great for testing out unfamiliar things and it's great for sharing code.
You can start typing straight away. But to run your code, you'll need to sign or log in. Logging in with a Google account gives you access to all non-commercial simulators and some commercial simulators:
To run commercial simulators, you need to register and log in with a username and password. Registration is free, and only pre-approved email's will have access to the commercial simulators.
209
//-----------------------------------------------------
// Title : Driver-Sequencer Handshake Mechanism
// Author : IKS (Jung Ik Moon)
// Description: For full description,
// see https://goo.gl/cj6Nts
//-----------------------------------------------------
module top;
timeunit 1ns;
timeprecision 1ps;
`include "uvm_macros.svh"
import uvm_pkg::*;
import my_pkg::*;
`include "my_env.sv"
`include "my_test.sv"
// clock and reset
bit clk = 1'b1;
bit rstn = 1'b1;
// interface
my_if u_my_if();
// assign clock and reset
assign u_my_if.clk = clk;
assign u_my_if.rstn = rstn;
// instantiate duv
duv u_duv(
.clk(u_my_if.clk),
.rstn(u_my_if.rstn),
.in(u_my_if.in),
.out(u_my_if.out)
);
// generate clock
initial forever #5 clk = ~clk;
// generate reset
initial begin
#10 rstn = 1'b0;
#10 rstn = 1'b1;
end
// set virtual interface
initial begin
uvm_config_db#(virtual my_if)::set(null, "uvm_test_top.env.agent.driver", "vif", u_my_if);
end
// run test
initial begin
run_test();
end
// dump waveform
initial begin
$dumpfile("dump.vcd");
$dumpvars;
end
endmodule: top
xxxxxxxxxx
`ifndef MY_ENV_SV
`define MY_ENV_SV
class my_env extends uvm_env;
`uvm_component_utils(my_env)
my_agent agent;
//---------------
// constructor
//---------------
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction: new
//---------------
// build phase
//---------------
function void build_phase(uvm_phase phase);
super.build_phase(phase);
agent = my_agent::type_id::create("agent", this);
endfunction: build_phase
endclass: my_env
`endif
xxxxxxxxxx
`ifndef MY_TEST_SV
`define MY_TEST_SV
class my_test extends uvm_test;
`uvm_component_utils(my_test)
my_env env;
my_sequence seq;
//---------------
// constructor
//---------------
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction: new
//---------------
// build phase
//---------------
function void build_phase(uvm_phase phase);
super.build_phase(phase);
env = my_env::type_id::create("env", this);
seq = my_sequence::type_id::create("seq");
endfunction: build_phase
//-----------------------------
// start of simulation phase
//-----------------------------
function void start_of_simulation_phase(uvm_phase phase);
uvm_factory factory = uvm_factory::get();
factory.print();
endfunction: start_of_simulation_phase
//-------------
// run phase
//-------------
task run_phase(uvm_phase phase);
super.run_phase(phase);
phase.raise_objection(this);
if (!seq.randomize()) `uvm_error(get_name(), "randomization fail");
seq.start(env.agent.sequencer);
phase.drop_objection(this);
endtask: run_phase
endclass: my_test
`endif
`ifndef MY_DRIVER_SV
`define MY_DRIVER_SV
class my_driver extends uvm_driver#(my_transaction);
`uvm_component_utils(my_driver)
virtual my_if vif;
//---------------
// constructor
//---------------
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction: new
//---------------
// build phase
//---------------
function void build_phase(uvm_phase phase);
super.build_phase(phase);
if (!uvm_config_db#(virtual my_if)::get(this, "", "vif", vif))
`uvm_fatal(get_name(), "virtual interface not set")
endfunction: build_phase
//-------------
// run phase
//-------------
virtual task run_phase(uvm_phase phase);
@(negedge vif.rstn) vif.in <= 4'h0;
@(posedge vif.rstn);
forever begin
`uvm_info(get_name(), "get_next_item", UVM_LOW)
seq_item_port.get_next_item(req);
`uvm_info(get_name(), "drive", UVM_LOW)
drive();
`uvm_info(get_name(), "item_done", UVM_LOW)
seq_item_port.item_done();
end
endtask: run_phase
//---------
// drive
//---------
virtual task drive();
@(negedge vif.clk) vif.in <= req.data;
endtask: drive
endclass: my_driver
`endif
xxxxxxxxxx
`ifndef MY_MONITOR_SV
`define MY_MONITOR_SV
class my_monitor extends uvm_monitor;
`uvm_component_utils(my_monitor)
//---------------
// constructor
//---------------
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction: new
endclass: my_monitor
`endif
xxxxxxxxxx
`ifndef MY_SEQUENCER_SV
`define MY_SEQUENCER_SV
typedef uvm_sequencer#(my_transaction) my_sequencer;
`endif
xxxxxxxxxx
`ifndef MY_TRANSACTION_SV
`define MY_TRANSACTION_SV
class my_transaction extends uvm_sequence_item;
`uvm_object_utils(my_transaction)
rand logic [3:0] data;
//---------------
// constructor
//---------------
function new(string name = "");
super.new();
endfunction: new
endclass: my_transaction
`endif
xxxxxxxxxx
`ifndef MY_AGENT_SV
`define MY_AGENT_SV
class my_agent extends uvm_agent;
`uvm_component_utils(my_agent)
my_driver driver;
my_sequencer sequencer;
my_monitor monitor;
//---------------
// constructor
//---------------
function new(string name, uvm_component parent);
super.new(name, parent);
endfunction: new
//---------------
// build phase
//---------------
function void build_phase(uvm_phase phase);
super.build_phase(phase);
driver = my_driver::type_id::create("driver", this);
sequencer = my_sequencer::type_id::create("sequencer", this);
monitor = my_monitor::type_id::create("monitor", this);
endfunction: build_phase
//------------------
// conncect phase
//------------------
function void connect_phase(uvm_phase phase);
super.connect_phase(phase);
driver.seq_item_port.connect(sequencer.seq_item_export);
endfunction: connect_phase
endclass: my_agent
`endif
xxxxxxxxxx
`ifndef MY_PKG_SV
`define MY_PKG_SV
package my_pkg;
`include "uvm_macros.svh"
import uvm_pkg::*;
`include "my_transaction.sv"
`include "my_driver.sv"
`include "my_sequencer.sv"
`include "my_monitor.sv"
`include "my_agent.sv"
`include "my_sequence.sv"
endpackage: my_pkg
`endif
xxxxxxxxxx
`ifndef MY_SEQUENCE_SV
`define MY_SEQUENCE_SV
class my_sequence extends uvm_sequence#(my_transaction);
`uvm_object_utils(my_sequence)
//---------------
// constructor
//---------------
function new(string name = "");
super.new();
endfunction: new
//--------
// body
//--------
virtual task body();
req = my_transaction::type_id::create("req");
`uvm_info(get_name(), "start_item", UVM_LOW)
start_item(req);
`uvm_info(get_name(), "randomize", UVM_LOW)
if (!req.randomize()) `uvm_error(get_name(), "randomization fail");
`uvm_info(get_name(), "finish_item", UVM_LOW)
finish_item(req);
endtask: body
endclass: my_sequence
`endif
xxxxxxxxxx
`ifndef MY_IF_SV
`define MY_IF_SV
interface my_if;
logic clk;
logic rstn;
logic [3:0] in;
logic [3:0] out;
endinterface: my_if
`endif
xxxxxxxxxx
//-----------------------------------------------------
// Title : Driver-Sequencer Handshake Mechanism
// Author : IKS (Jung Ik Moon)
// Description: For full description,
// see https://goo.gl/cj6Nts
//-----------------------------------------------------
module duv(
input wire clk,
input wire rstn,
input wire [3:0] in,
output reg [3:0] out
);
always @(posedge clk or negedge rstn) begin
if (!rstn) out <= 4'h0;
else out <= in;
end
endmodule: duv
xxxxxxxxxx
MIT License
Copyright (c) 2018 IKS
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
Your account is not validated. If you wish to use commercial simulators, you need a validated account.
If you have already registered (or have recently changed your email address), but have not clicked on the link in the email we sent you, please do so. If you cannot find the email, please check your spam/junk folder. Or click here to resend the email.
If you have not already registered for a full account, you can do so by clicking below. You will then need to provide us with some identification information. You may wish to save your code first.
Creating, deleting, and renaming files is not supported during Collaboration. To encourage development of these features for Collaboration, tweet to @EDAPlayground
This playground may have been modified. Please save or copy before starting collaboration.
Your exercise has been submitted.