Reputation: 19
I have a code similar to the following
module testModule(
input Clk,
input [2:0] Counter,
output [1:0] OutVar1,
output [1:0] OutVar2
);
localparam logic [7:0] mask = 8'h50;
// CODE 1
always_ff @(posedge Clk) begin
case (mask[{Counter[1:0], 1'b0} +: 2])
2'h0 : OutVar1 <= 2'h0;
2'h1 : OutVar1 <= 2'h1;
2'h2 : OutVar1 <= 2'h2;
2'h3 : OutVar1 <= 2'h3;
default: OutVar1 <= 2'hX;
endcase
end
// CODE 2
always_ff @(posedge Clk) begin
case (mask[(Counter[1:0]<<1) +: 2])
2'h0 : OutVar2 <= 2'h0;
2'h1 : OutVar2 <= 2'h1;
2'h2 : OutVar2 <= 2'h2;
2'h3 : OutVar2 <= 2'h3;
default: OutVar2 <= 2'hX;
endcase
end
endmodule
Counter is a input that goes 0, 2, 4, 6, 0, 2, 4, etc. And I expected CODE 1 and CODE 2 to behave the same but when counter is 2 and 6 (counter[1:0] is 2) I hit the case 2'h1 in CODE 1 (correct) and 2'h0 in CODE 2 (wrong).
I have not checked yet what is the behaviour if counter goes 0, 1, ..., 7, 0, 1, etc.
I do not have a testbed because this code is part of a large project. I saw the problem after simulation and seeing the waves.
What am I missing?
Upvotes: 0
Views: 282
Reputation: 13937
I suspect you're missing that only 2 bits are used to calculate the answer in "CODE 2", because it is a so-called self-determined expression. So, Verilog takes the expression:
counter[1:0]<<1
and needs to decide how many bits to use for the answer. This is what it does: it looks at how many bits there are on the left hand side of the shift operator (2) and uses that to put the result in. How could it do anything else? The number of bits on the right hand side (32) is basically irrelevant (unless you think Verilog should use 2^31-1 bits for the result!). So, you get an overflow - the left hand side of the result of the shift is truncated.
See this answer here.
Upvotes: 1