Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Verilator not handling individual generate/if blocks. #1148

Closed
veripoolbot opened this issue Mar 27, 2017 · 2 comments
Closed

Verilator not handling individual generate/if blocks. #1148

veripoolbot opened this issue Mar 27, 2017 · 2 comments

Comments

@veripoolbot
Copy link

@veripoolbot veripoolbot commented Mar 27, 2017


Author Name: Udi Finkelstein
Original Redmine Issue: 1148 from https://www.veripool.org


the following code produces a warning:

  test2 #( .P(3)) t2 ();
endmodule

module test2 #(P=10);
generate
  if (P>0)
  begin
     wire [P:0]x;
  end
  if (P > 0)
  begin
     assign x = {(P+1){1'b0}};
  end
endgenerate
endmodule
</code>
$ verilator --cc -sv test.sv
%Warning-IMPLICIT: test.sv:14: Signal definition not found, creating implicitly: x
%Warning-IMPLICIT: Use "/* verilator lint_off IMPLICIT */" and lint_on around source to disable this message.
%Warning-WIDTH: test.sv:14: Operator ASSIGNW expects 1 bits on the Assign RHS, but Assign RHS's REPLICATE generates 4 bits.
%Error: Exiting due to 2 warning(s)
%Error: Command Failed /auto/csiproj1/udif/local/bin/verilator_bin --cc -sv test.sv
</code>

A slightly modified code:

  test2 #( .P(3)) t2 ();
endmodule

module test2 #(P=10);
generate
  if (P>0)
  begin
     wire [P:0]x;
     assign x = {(P+1){1'b0}};
  end
endgenerate
endmodule
</code>

produces no warnings.

Yes, this module does nothing, but it's a minimum complete verifiable example (mvce).

@veripoolbot

This comment has been minimized.

Copy link
Author

@veripoolbot veripoolbot commented Mar 27, 2017


Original Redmine Comment
Author Name: Todd Strader (@toddstrader)
Original Date: 2017-03-27T13:00:37Z


I think Verilator is right. If you were to name your two generate blocks it should be more clear. You're declaring a wire x and getting something like:
test.test2.unamed_block_0.x

And then you are assigning x in a second generate block which means you are trying to use something like:
test.test2.unamed_block_1.x

These two signals are not the same. If you named the blocks you should be able to assign the x declared in the first generate block from the second via a dotted reference (but this is dirty and I suspect not what you want to do).

Is there some reason you can't declare and use the signal all within the same generate block?

@veripoolbot

This comment has been minimized.

Copy link
Author

@veripoolbot veripoolbot commented Mar 27, 2017


Original Redmine Comment
Author Name: Udi Finkelstein
Original Date: 2017-03-27T14:04:30Z


Thanks for the explanation. I ran this through VCS and found similar issues, while CVC seems to grok this, but I haven't tested the output.

I actually never gave any thought to the naming hierarchies, and always treated generate/if as a language-supported ifdef that can be used with multiple instances driving different parameter values (which you can't do with ifdef).

The reason I did this in the first place was that the original block had 5-6 different parameters, and doing everything within one scope would have caused lots of redundancy (e.g. 4 wires x,y,z,w where each is defined only if the respective parameter X,Y,Z,W is > 0, and then an output assignment that depends on various combinations of X/Y/Z/W values).

It seems I will have no choice but to rewrite this the long way.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
1 participant
You can’t perform that action at this time.