Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- //interface to group signals
- timeunit 1ns;
- timeprecision 1ns;
- interface candy_vending_intf(input bit clk);
- logic rst;
- logic n;
- logic d;
- logic q;
- logic dispense;
- logic rn;
- logic rd;
- modport DUT(
- input n,d,q,rst,clk,
- output dispense,rn,rd
- );
- modport TEST(
- input dispense,rn,rd,clk,
- output n,d,q,rst
- );
- endinterface:candy_vending_intf
- class Transaction;
- rand bit n;
- rand bit d;
- rand bit q;
- constraint C1{{n,d,q} dist{3'b100:=120,3'b010:=50,3'b001:=20};}
- endclass:Transaction
- class Generator;
- //declare handles
- Transaction trans;
- mailbox drv_mb;//mailbox is an sv builtin unit
- //constructor function
- function new(mailbox aa);
- drv_mb =aa;
- endfunction
- task main(int count);
- repeat (count) begin
- trans= new();
- if(!trans.randomize)
- $fatal (0,"............Randomisation Failed!!!..........");
- drv_mb.put(trans);
- end
- endtask
- endclass:Generator
- class Driver;
- //declare handles
- Transaction trans;
- mailbox gen2drv;
- virtual candy_vending_intf.TEST h_tb_port;//h_tb_port is an handle to interface candy_vending_intf
- shortint nickels,dimes,quarters;
- bit done;
- function new(virtual candy_vending_intf.TEST h_tb_port, mailbox bb);
- this.h_tb_port=h_tb_port;
- gen2drv=bb;
- endfunction
- task reset();
- @(posedge h_tb_port.clk);
- h_tb_port.rst<=0;
- $display("REST Started...@%0t",$time);
- h_tb_port.n<=0;
- h_tb_port.d<=0;
- h_tb_port.q<=0;
- #12ns;
- h_tb_port.rst<=1;
- $display("RESET Ended...@%0t",$time);
- endtask
- task drive(int count);
- repeat (count) begin:loop
- gen2drv.get(trans);
- //count coins
- nickels += trans.n;
- dimes += trans.d;
- quarters += trans.q;
- @(posedge h_tb_port.clk);
- h_tb_port.n<=trans.n;
- h_tb_port.d<=trans.d;
- h_tb_port.q<=trans.q;
- @(posedge h_tb_port.clk);
- h_tb_port.n<=0;
- h_tb_port.d<=0;
- h_tb_port.q<=0;
- @(negedge h_tb_port.clk);
- if(h_tb_port.dispense)
- repeat (20) @(posedge h_tb_port.clk);
- end:loop
- done=1'b1; //all transactions done..
- $display("DRIVER::\t nickels =%0d, DIMES = %0d ,QUARTERS = %0d\n",nickels,dimes,quarters);
- endtask
- endclass:Driver
- program automatic tb_candy_vending(tb_port);
- candy_vending_intf.TEST tb_port;
- //declare all handles
- Transaction trans;
- mailbox drv_mb;
- Generator gen;
- Driver drv;
- int rpt_count=400;
- virtual candy_vending_intf.TEST h_tb_port=tb_port;//declare and initilaise theinterface handle
- //apply inputs
- initial begin
- drv_mb=new(1);//depth-1
- gen =new(drv_mb);
- drv = new(h_tb_port,drv_mb);
- drv.reset();//reset dut
- repeat (5) @(posedge tb_port.clk);
- fork:fj1
- gen.main(rpt_count);
- drv.drive(rpt_count);
- join:fj1
- end
- initial
- begin
- $recordfile("candy_vending_ver2.trn");
- $recordvars();
- end
- endprogram
- module top_candy_vending_ver2;
- bit clk;
- initial
- begin
- clk=1'b1;
- forever #5 clk++;
- end
- candy_vending_intf IF1(.clk(clk));
- candy_vending_ver2 DES(
- .cv_ifc(IF1.DUT)
- );
- tb_candy_vending TESTBLK(
- .tb_port(IF1.TEST)
- );
- endmodule
- module candy_vending_ver2(cv_ifc);
- candy_vending_intf.DUT cv_ifc;
- localparam[3:0]
- S0=0,
- S5=1,
- S10=2,
- S15=3,
- S20=4,
- S25=5,
- S30=6,
- S35=7,
- S40=8,
- S45=9,
- DUM=10,
- RD2=11;
- reg[3:0] cst,nst;
- always@(posedge cv_ifc.clk or negedge cv_ifc.rst)
- begin
- if(!cv_ifc.rst)
- cst<=S0;
- else
- cst<=nst;
- end
- always@(*)
- begin
- case(cst)
- S0:if(cv_ifc.n) nst=S5;
- else if(cv_ifc.d) nst=S10;
- else if(cv_ifc.q) nst=S25;
- else nst=cst;
- S5:if(cv_ifc.n) nst=S10;
- else if(cv_ifc.d) nst=S15;
- else if(cv_ifc.q) nst=S30;
- else nst=cst;
- S10:if(cv_ifc.n) nst=S15;
- else if(cv_ifc.d) nst=S20;
- else if(cv_ifc.q) nst=S35;
- else nst=cst;
- S15:if(cv_ifc.n) nst=S20;
- else if(cv_ifc.d) nst=S25;
- else if(cv_ifc.q) nst=S40;
- else nst=cst;
- S20:if(cv_ifc.n) nst=S25;
- else if(cv_ifc.d) nst=S30;
- else if(cv_ifc.q) nst=S45;
- else nst=cst;
- S25,S30,S35,S40,RD2:nst=S0;
- S45:nst=DUM;
- DUM:nst=RD2;
- endcase
- end
- assign cv_ifc.dispense=(cst==S25)|(cst==S30)|(cst==S35)|(cst==S40)|(cst==S45);
- assign cv_ifc.rd=(cst==S35)|(cst==S40)|(cst==S45)|(cst==RD2);
- assign cv_ifc.rn=(cst==S30)|(cst==S40);
- endmodule
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement