Verilog Nested For Loop – Troubleshooting Unexpected Behavior

digital-logicfpgaverilogvivado

I am having trouble with a simulation of an 8-bit full adder i wrote in verilog. Basically I have two integers that I feed into the full adder, I add them together and I check if the result is as expected. Here is the code:

full_adder_Nb_tb.v:

`timescale 1ns / 1ps
`include "config.v"

module full_adder_Nb_tb #(parameter  N = 8)();
reg [N-1:0] a;
reg [N-1:0] b;
wire [N-1:0] s;
wire co;
integer i, j;
integer error_cnt;

full_adder_Nb #(N) test_module (a, b, s, co); 

initial
begin
    $display("TESTING full_adder_Nb.v");
    error_cnt = 0;
    for (i = 0; i < 2^(N-1); i=i+1) begin : outer_loop
        a = i;
        for (j = 0; j < 2^(N-1); j=j+1) begin : inner_loop
            b = j;
            #5;

            if (s != (i+j)%(2^(N-1)) || co != (i+j)/(2^(N-1)))
            begin
                error_cnt = error_cnt + 1;
                `ifdef VERBOSE
                    $display("There was an ERROR. Inputs: a=%d,b=%d, outputs: s=%d, co=%d. Expecected value: s=%d, co=%d", a, b, s, co, (i+j)%(2^(N-1)), (i+j)/(2^(N-1)));
                `endif  
            end        
        end : inner_loop        
    end : outer_loop

    // SIMULATION FINAL OUTPUT
    if (error_cnt == 0)
    begin
        $display("full_adder_Nb.v WORKS correctly.");
    end
    else
    begin
        $display("full_adder_Nb.v does NOT WORK. It has %d errors!", error_cnt);
    end

    #20;
    $finish;

end
endmodule

This is the result of the simulation:
simulation_result

As you can see integer i and reg a are both stuck at 0, while j and b are behaving as inteded. I do realise that this does not fully test this circuit (I intend to add negative numbers simulation).

I am grateful for any hints.

Best Answer

You have problems with the Operator Precedence.

The comparison ( < ) has higher precedence then you EXOR operator ( ^ ).

Thus first j < 2 is calculated as true (1) or false (0).
Then that is EXOR-ed with 7, which gives either 6 or 7.
But it never gives 0 (false) so the loop does not finish.

Try: j < (2^(N-1)) or what you probably want: j < (1<<(N-1))