The optimization correctly realizes that the two ways are equivalent and selects one of these, the version in which we expand all the zero bits left of b, append b and OR-ing that with the other input:
module foo(
input wire [31:0] x,
input wire b,
output wire [63:0] out
);
wire [31:0] r1;
assign r1 = x | {31'h0000_0000, b};
assign out = {r1, r1};
endmodule
Expected Result
It would probably be more specific to only manipulate the bit in question without bothering OR-ing zeroes with all the rest, so my expectation would be that the other implementation would be chosen (and, in fact that a x | (b as u32); would be converted to this):
Maybe this actually does not make any difference as synthesis-tools might figure this out anyway and don't emit OR gates where not needed, so this should be first tested to see if it is worthwhile considering as an optimization.
Consider the following code that generates the same output --
OR
-ing the last bit with a bool -- in two different ways:/tmp/foo.x
Only the last bit should be affected, all the other bits stay as-is from the input
x
.Let's generate code from this
Result
The optimization correctly realizes that the two ways are equivalent and selects one of these, the version in which we expand all the zero bits left of
b
, appendb
andOR
-ing that with the other input:Expected Result
It would probably be more specific to only manipulate the bit in question without bothering
OR
-ing zeroes with all the rest, so my expectation would be that the other implementation would be chosen (and, in fact that ax | (b as u32);
would be converted to this):Remarks
Maybe this actually does not make any difference as synthesis-tools might figure this out anyway and don't emit
OR
gates where not needed, so this should be first tested to see if it is worthwhile considering as an optimization.