My code is compiling well, but it does not work when i simulate it.
It displays "error loading design".
i think that input and output port is wrong among these modules.
but i can not find them..
please help me where the error is in my code.
module tb_modulo_60_binary;
reg t_clk, reset;
wire [7:0] t_Y;
parameter sec = 30;
always #(sec) t_clk = ~t_clk;
modulo_60_binary M1 (t_Y, t_clk, reset);
initial begin
t_clk = 1; reset =1; #10;
reset = 0; #3050;
$finish;
end
endmodule
module modulo_60_binary(y, clk, reset);
output [7:0] y;
input reset, clk;
wire TA1, TA2, TA3, JA2, JA4;
reg [7:0] y;
assign TA1 = 1;
assign TA2 = (~y[6]) && y[4];
assign TA3 = (y[5] && y[4]) || (y[6] && y[4]);
assign JA2 = ~y[3];
assign JA4 = y[1]&&y[2];
jk_flip_flop JK1 (1, 1, clk, y[0]);
jk_flip_flop JK2 (JA2, 1, y[0], y[1]);
jk_flip_flop JK3 (1, 1, y[1], y[2]);
jk_flip_flop JK4 (JA4, 1, y[1], y[3]);
t_flip_flop T1 (TA1, clk, y[4]);
t_flip_flop T2 (TA2, clk, y[5]);
t_flip_flip T3 (TA3, clk, y[6]);
always #(negedge clk)
begin
if(reset)
y <= 8'b00000000;
else if(y == 8'b01110011)
y <= 8'b00000000;
end
endmodule
module t_flip_flop(t, clk, q);
input t, clk;
output q;
reg q;
initial q=0;
always #(negedge clk)
begin
if(t == 0) q <= q;
else q <= ~q;
end
endmodule
module jk_flip_flop(j, k, clk, Q);
output Q;
input j, k, clk;
reg Q;
always #(negedge clk)
if({j,k} == 2'b00) Q <= Q;
else if({j,k} == 2'b01) Q <= 1'b0;
else if({j,k} == 2'b10) Q <= 1'b1;
else if({j,k} == 2'b11) Q <= ~Q;
endmodule
Your y signal in modulo_60_binary is being driven in two places:
By bit JK# and T# instances
The reset logic that assigns all bits of y to zeros
Flops and comb-logic must have one clear driver. This is one of the fundamental differences between software and hardware languages.
The rest of my answer assuming the use of the JK and T flops are a design requirement. Therefore you need to delete the always block that assigns y to zeros and and make y a wire type.
Fixing the logic to the T flops is easy. Simply add a conditional statement. Example:
wire do_rst = reset || (y == 8'b01110011);
assign TA1 = do_rst ? y[4] : 1;
assign TA2 = do_rst ? y[5] : (~y[6]) && y[4];
assign TA3 = do_rst ? y[6] : (y[5] && y[4]) || (y[6] && y[4]);
The JK flops is harder because the output of one flop is the clock of another. I'll advice that the clock input for each JK flop should be clk, otherwise you are asking for a design headache for reset when it's y bits are non power of two minus one values (eg 1,3,7,15). This means you need to re-evaluate your JA# logic and add KA# logic (hint the do_rst from above will help). I'm not going to do the work for you beyond this.
There is the option of the asynchronous reset approach, but for this design I will advice ageist it. The reset pulse could be too short on silicon with the conditional reset for y == a particular value(s), which can result in an undependable partial reset. You could add synthesis constraints/rules to keep the push wide enough, but that is just patching a brittle design. Better to design it robust at the beginning.
FYI: y[7] does not have a driver and the module declaration of instance T3 has a typo.
Related
I learned two ways of writing pipeline(unblocking and blocking), I wonder which is better?
My personal opinion is that the second one is tedious and I don't understand why so many wire are needed.
Also, is there any standard style(template) of writing pipeline like FSM in verilog?
Thanks in advance.
module simplePipeline
#(
parameter WIDTH = 100
)
(
input clk,
input [WIDTH - 1 : 0] datain,
output [WIDTH - 1: 0] dataout
);
reg [WIDTH - 1 : 0] piprData1;
reg [WIDTH - 1 : 0] piprData2;
reg [WIDTH - 1 : 0] piprData3;
always #(posedge clk) begin
piprData1 <= datain;
end
always #(posedge clk) begin
piprData2 <= piprData1;
end
always #(posedge clk) begin
piprData3 <= piprData2;
end
assign dataout = piprData3;
endmodule
module blockingPipeline#2
(
parameter WIDTH = 100
)
(
input clk,
input rst,
input validIn,
input [WIDTH - 1 : 0] dataIn,
input outAllow,
output wire validOut,
output wire [WIDTH - 1 : 0] dataOut
);
reg pipe1Valid;
reg [WIDTH - 1 : 0] pipe1Data;
reg pipe2Valid;
reg [WIDTH - 1 : 0] pipe2Data;
reg pipe3Valid;
reg [WIDTH - 1 : 0] pipe3Data;
/*------------------------PIPE1 LOGIC------------------------*/
wire pipe1AllowIn;
wire pipe1ReadyGo;
wire pipe1ToPipe2Valid;
assign pipe1ReadyGo = 1'b1
assign pipe1AllowIn = ! pipe1Valid || pipe1ReadyGo && pipe2AllowIn;
assign pipe1ToPipe2Valid = pipe1Valid && pipe1ReadyGo
always #(posedge clk)begin
if( rst ) begin
pipe1Vali <= 1'b0;
end
else if(pipe1AllowIn)begin
pipe1Valid <= validIn;
end
ifvalidIn && pipe1AllowIn)begin
pipe1Data <= dataIn;
end
end
/*------------------------PIPE2 LOGIC------------------------*/
wire pipe2AllowIn;
wire pipe2ReadyGo;
wire pipe2ToPipe3Valid;
assign pipe2ReadyGo = 1'b1;
assign pipe2AllowIn = ! pipe2Valid || pipe2ReadyGo && pipe3AllowIn;
assign pipe2ToPipe3Valid = pipe2Valid && pipe3ReadyGo;
always #(posedge clk)begin
if( rst ) begin
pipe2Valid <= 1'b0;
end
else if(pipe2AllowIn)begin
pipe2Valid <= pipe1ToPipe2Valid;
end
if(pipe1ToPipe2Valid && pipe2AllowIn)begin
pipe2Data <= pipe1Data;
end
end
/*------------------------PIPE3 LOGIC------------------------*/
wire pipe3AllowIn;
wire pipe3ReadyGo;
assign pipe3ReadyGo = 1'b1;
assign pipe3AllowIn = ! pipe3Valid || pipe3ReadyGo && outAllow;
always #(posedge clk)begin
if( rst ) begin
pipe3Valid <= 1'b0;
end
else if(pipe3AllowIn)begin
pipe3Valid <= pipe2ToPipe3Valid;
end
if(pipe2ToPipe3Valid && pipe3AllowIn)begin
pipe3Data <= pipe2Data;
end
end
assign validOut = pipe3Valid && pipe3ReadyGo;
assign dataOut = pipe3Data;
endmodule
The problem with the first version is that there seems to be no clock gate at all. Unless your clock is well gated on a higher level or the pipeline is used every cycle you will waste a lot of power by (unnecessarily) toggling each stage of the pipeline every cycle.
As good practice, the second one seems "better" in the sense that when you design a hardware circuit part you might want offer great control possibilities. Generally speaking, since your code will be implemented in the silicon forever (or in your FPGA with painful reconfiguration) that would be a real problem to not have enough controls capacities, because you can't really add some afterward.
As an example you already mentioned in the comments that you'll have to stall the pipeline, so of course you need more wires to do it. You will also need to reset the pipeline sometimes, this is the purpose of the rst signal.
However, more signals means more silicon surface (or more FPGA resources using) which generally come with a greater price. One can argue that only one or two wires will not makes such great difference for a chip, which is true, but if you re-use your pipeline thousand times on the circuit it will be much more significant.
For me the first implementation can be relevant only with really strong optimization requirements at circuit level like for an ASIC, where you exactly know the overall wanted behavior.
I made 4_to_1 MUX with 2_to_1 MUX. I used always syntax. The output is delayed one time unit, but I don't know why.
When I change the always condition of 4_to_1 MUX's module sel to *, it works well. Why is this working?
module MUX_2_to_1 (
a0,a1,sel,out);
input [3:0]a0;
input [3:0]a1;
input sel;
output reg [3:0]out;
always #(sel)
begin
if (sel == 0)
out <= a0;
else if (sel == 1)
out <= a1;
end
endmodule
*
module MUX_4_to_1(
x0,x1,x2,x3,sel,out);
input [3:0]x0;
input [3:0]x1;
input [3:0]x2;
input [3:0]x3;
input [1:0]sel;
output reg [3:0]out;
wire [3:0]w0;
wire [3:0]w1;
MUX_2_to_1 m0 (x0,x1,sel[0],w0);
MUX_2_to_1 m1 (x2,x3,sel[0],w1);
always #(sel)
begin
if(sel[1] == 0)
out <= w0;
else if (sel[1] == 1)
out <= w1;
end
endmodule
*
`timescale 100ps/1ps
module Testbench_Mux;
reg [3:0]x0;
reg [3:0]x1;
reg [3:0]x2;
reg [3:0]x3;
reg [1:0]sel;
wire [3:0]out;
MUX_4_to_1 m0 (x0,x1,x2,x3,sel,out);
initial
begin
x0 = 4'b0001; x1 = 4'b0010; x2 = 4'b0100; x3 = 4'b1000;
#0 sel = 2'b00;
#5 sel = 2'b01;
#5 sel = 2'b10;
#5 sel = 2'b11;
#5 $stop;
end
endmodule
You are not using recommended Verilog coding practices for combinational logic. One problem is that you used an incomplete sensitivity list:
always #(sel)
Since there are 2 other signals, w0 and w1, which are read in the always block, they must also be in the sensitivity list. The verbose way to do this is:
always #(sel or w0 or w1)
The preferred way to do this is to use the compact * syntax:
always #(*)
This assures that the always block will be triggered when any change occurs to any signal read in the block.
Another issue is that you should always use blocking assignments for combinational logic. There is ample documentation out there as to the reason.
Change <= to =:
always #(*)
begin
if(sel[1] == 0)
out = w0;
else if (sel[1] == 1)
out = w1;
end
If you don't follow these recommendations, you get undesired simulation results.
You should change your MUX_2_to_1 module as well.
I am working with a verilog module (shown below) has two always blocks. Won't there be some sort of race condition since one block sets a register and the other uses the register. What kind of issues would this cause?
Thanks,
Stephen
module XYZ
(
input wire CLK,
input wire Reset,
input wire nReset,
input wire [15:0] X,
input wire [15:0] A,
input wire T,
input wire B,
output reg M
);
assign C = X > A;
reg P;
reg N;
always #(posedge CLK, negedge nReset)
begin
if (~nReset)
begin
P <= 1;
N <= 1;
end else begin
if (Reset)
begin
P <= 1;
N <= 1;
end else begin
P <= T? 1: ((C & ~M)? 0: P);
N <= B? 1: ((M & ~C)? 0: N);
end
end
end
always #(posedge CLK, negedge nReset)
begin
if (~nReset)
begin
M <= 0;
end else begin
if (Reset)
begin
M <= 0;
end else begin
M <= M? ~(N & ~C): (P & C);
end
end
end
endmodule
No, there is no race condition. Verilog is an event-driven simulator. Posedge (unless there is a glitch in the clock or reset) is usually executed once per the simulation tick. If you use non-blocking assignments correctly (and it looks like you did), every always block triggered by an edge will use old versions of the input variable values, the values which existed before the clock edge.
Here is a simplified example:
always #(posedge clk)
r <= in;
always #(posedge clk)
out <= r;
What happens in this situation is the following:
r will be assigned the value of in later at the simulation tick, after the always blocks have been evaluated (see the nba scheduling region).
since r has not been yet really changed, the out will be scheduled to be assigned the value of r with the value before the edge.
If r was 0 before the edge and in was 1, at the end of the simulation r will become 1 and out will become 0.
This mimics behavior for real flops in hardware.
In your case it might look as a loop dependency. In reality it it none. For the same reason as above the M value will be the one from before the the posedge and will not cause any race. Flops cannot be involved in the combinational loops due to their properties logical properties.
I completely Agree with the above answer and i would suggest some more to the above answer, when i started learning Verilog i too got the same doubt and these lines from a ref. book clarified my doubts. I am coping the statement here and
for further doubts u can comment here or u can see the
Ref. book page number 135
Book name :Verilog HDL: A Guide to Digital Design and Synthesis,
Second Edition By Samir Palnitkar
nonblocking statements used in Example 2 eliminate the race condition.
At the positive edge of clock, the values of all right-hand-side
variables are "read," and the right-hand-side expressions are
evaluated and stored in temporary variables. During the write
operation, the values stored in the temporary variables are assigned
to the left-handside variables. Separating the read and write
operations ensures that the values of registers a and b are swapped
correctly, regardless of the order in which the write operations are
performed.
On the downside, nonblocking assignments can potentially cause a
degradation in the simulator performance and increase in memory usage.
//Example 2: Two concurrent always blocks with nonblocking
//statements
always #(posedge clock)
a <= b;
always #(posedge clock)
b <= a;
And u can use this type of coding style not compulsory but for the ease of debugging and to fasten simulation u can reduce the usage of begin-end blocks where ever possible
module XYZ
(
input wire CLK,
input wire Reset,
input wire nReset,
input wire [15:0] X,
input wire [15:0] A,
input wire T,
input wire B,
output reg M
);
reg P,N;
always #(posedge CLK, negedge nReset)
if (~nReset)begin
P <= #10 1;
N <= #10 1;
end else if (Reset) begin
P <= #10 1;
N <= #10 1;
end else begin
P <= #10 T ? 1 : ((C & ~M) ? 0: P);
N <= #10 B ? 1 : ((M & ~C) ? 0: N);
end
always #(posedge CLK, negedge nReset)
if (~nReset) M <= #10 0 ;
else if ( Reset) M <= #10 0 ;
else M <= #10 M ? ~(N & ~C): (P & C);
assign C = X > A;
endmodule
I want to get a register absolute value inside an always# block with a clock but I'm getting the abs of the previous value instead of the current one.
I saw this before and here is what I am doing:
reg signed [7:0] x;
reg signed [7:0] xabs;
...
always # (posedge CLK or posedge RST)
begin
...
if($signed(x) < 0)
xabs <= -$signed(x);
else
xabs <= x;
...
end
Is there anything that I am doing wrong?
waveform:
waveform
If you use always #posedge, then xabs will be assigned a cycle after x is assigned.
If you want xabs to change as soon as x changes, you can use a always #* which triggers immediately.
reg [32-1:0] xabs;
always #* begin
...
if($signed(x) < 0)
xabs = -$signed(x);
else
xabs = x;
...
end
Our you can make xabs a wire and use an assign.
wire [32-1:0] xabs;
assign xabs = ($signed(x) < 0) ? -$signed(x) : x;
I am having trouble making testbenches. It is far into the quarter in my school but I feel like I am missing out on some fundamentals.
Here I am trying to make a 2 by 4 decoder, but I want to simulate it inside verilog.
module decoder2to4(x, enable, y);
input [1:0] x; //this is my decoder input
input enable;
output [3:0] y;
reg [3:0] y;
always #(x, enable ) //
begin
if(enable==0) //if enable isn't on, all outputs WON'T OUTPUT correct and give us 1111
y = 4'b1111;
else //if enable is high...
if (x == 2'b00) //...then we check our inputs and give corresponding outputs
y = 4'b0001;
if (x == 2'b01)
y = 4'b0010;
if (x == 2'b10)
y = 4'b0100;
if (x == 2'b11);
y = 4'b1000;
end
endmodule
This is my simulation file ~ did i write it correctly ?
module testbench_2to4decoder;
reg [1:0] x; //use reg not wire to assign values
wire [3:0] y; //for the outputs
2to4Decoder uut(x,y);
initial begin
x = 2'b00;
enable = 1'b0; //keep it off
#10 //wait some time
enable = 1'b1; //turn enable on
#10; //wait some time
x = 2'b01; //input 01
#10; //wait some time
x = 2'b10; //input 10
#10; //then
x = 2'b11; //input 11
#10;
enable = 1'b0; //turn it off
#10;
end
endmodule
You are not instantiating the design properly. Firstly, enable is not connected. enable is not even declared in testbench.
Also, the module name is wrong. Instead of following:
2to4Decoder uut(x,y);
You must have:
decoder2to4 uut(x,enable, y);
Using a reset logic is encouraged to have default values of output. But since this is a combinational circuit, it is not mandatory here.
The inputs can be provided by using a for or repeat loop and increment variable x in it. But this is just for coding efficiency.
Rest of the things seems to be fine. Refer Module instantiation link.