Reputation: 45
Can anyone help me in writing verilog test bench code for the following code ! I have try but it's doesn't work !
module top(clock_in, Reset, Hold, up_down, Led_Out, f);
input clock_in, Reset, Hold, up_down;
output [6:0] Led_Out;
output wire [3:0] f;
wire pulse;
clock_design temp0(clock_in, pulse);
up_down_counter temp1(pulse, Reset, Hold, up_down, f);
led7 temp2(Led_Out, f);
endmodule
led7 :
module led7(iOut, iQ);
output reg [6:0] iOut;
input [3:0] iQ;
always @(iQ)
case (iQ)
4'b0000: iOut = 7'b0000001; //0
4'b0001: iOut = 7'b1001111; //1
4'b0010: iOut = 7'b0010010; //2
4'b0011: iOut = 7'b0000110; //3
4'b0100: iOut = 7'b1001100; //4
4'b0101: iOut = 7'b0100100; //5
4'b0110: iOut = 7'b0100000; //6
4'b0111: iOut = 7'b0001111; //7
4'b1000: iOut = 7'b0000000; //8
4'b1001: iOut = 7'b0000100; //9
default: iOut = 7'b0000000; //default
endcase
endmodule
up_down_counter :
module up_down_counter (Clock,Reset,Hold,up_down,Q);
input Clock,Reset,Hold,up_down;
output reg [3:0] Q;
integer direction;
always @(posedge Clock)
begin
if(up_down)
direction = 1;
else
direction = -1;
if (!Reset && direction == 1)
Q <= 0;
else if(!Reset && direction == -1)
Q <= 1001;
else if (!Hold)
Q <= Q + direction;
if (direction==1 && Q[0]==1 && Q[1]==0 &&Q[1]==0 && Q[3]==1)
Q <= 0;
else if (direction==-1 && Q[0]==0 && Q[1]==0 &&Q[2]==0 && Q[3]==0)
Q <= 1001;
end
endmodule
clock_design :
module clock_design (clock_in,clock_out);
input clock_in;
output clock_out;
parameter which_clock=1;
reg [31:0] divided_clocks=0;
always @(posedge clock_in)
divided_clocks = divided_clocks +1;
assign clock_out = divided_clocks[which_clock];
endmodule
My Test-bench code
module counter_tb;
reg [6:0] Led_Out_tb;
wire [3:0] f_tb;
reg clock_in_tb, Reset_tb, Hold_tb, up_down_tb;
top dut(clock_in_tb, Reset_tb,Hold_tb, up_down_tb, Led_Out_tb, f_tb);
initial begin
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 1;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 1;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
#10 clock_in_tb = 0;Hold_tb = 0;Reset_tb = 1; up_down_tb = 0;
end
endmodule
Upvotes: 0
Views: 20561
Reputation: 20514
Testbench wise I would set up a clock and reset like this :
reg clk ; //Rising edge every 10 timesteps
initial begin
clk = 0;
#5;
forever begin
#5 clk = ~clk;
end
end
// TB Reset_tb
reg Reset_tb
initial begin
Reset_tb = 0;
@(posedge clk);
@(posedge clk);
Reset_tb = 1;
end
And for the actual test something like :
//The actual test
initial begin
Hold_tb = 0;
up_down_tb = 1;
repeat (50) begin
@(posedge clk);
end
up_down_tb = 1;
repeat (50) begin
@(posedge clk);
end
$finish();
end
About the Code
You have a section of what looks like it should be combinatorial logic in an always @(posedge clk)
block.
always @(posedge Clock)
begin
if(up_down)
direction = 1;
else
direction = -1;
I think this should be :
always @* begin
if(up_down)begin
direction = 1;
end
else begin
direction = -1;
end
end
If you do not include begin end
the if statements only apply to the next line. I would use begin ends much more frequently so your code is explicitly shows your intent.
You have the following section of code :
if (!Reset && direction == 1)
Q <= 0;
else if(!Reset && direction == -1)
Q <= 1001;
else if (!Hold)
Q <= Q + direction;
if (direction==1 && Q[0]==1 && Q[1]==0 &&Q[1]==0 && Q[3]==1)
Q <= 0;
else if (direction==-1 && Q[0]==0 && Q[1]==0 &&Q[2]==0 && Q[3]==0)
Q <= 1001;
Is there a missing else on the 4th if? if (direction==1 && Q[0]==1 && Q[1]==0 &&Q[1]==0 && Q[3]==1)
I would avoid the use of integer types in RTL as the are often overkill, especially here were you are just storing 1 or -1 that really only needs a 1 bit value. Regs and wires can be signed :
reg signed signed_reg ;
reg signed [7:0] signed_reg8;
You can also declare constant as signed :
reg_signed = 1'sd-1 ; //1Bit Signed Decimal value -1
I find it bad practise to use mixed case signal names, I always use lower case. Constants like parameters and localparams are all upper case. This makes typos a bit less likely, you could spend ages trying to workout why something is not working then you realise one of the connection was using a lower case instead of upper case first character.
Upvotes: 8