Fix const-bit-op-tree with single-bit masks (#5993) (#5998)

This commit is contained in:
Yutetsu TAKATSUKASA 2025-05-10 19:01:15 +09:00 committed by GitHub
parent d22608a49f
commit 100e3d7702
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 31 additions and 1 deletions

View File

@ -125,6 +125,7 @@ class ConstBitOpTreeVisitor final : public VNVisitorConst {
void updateBitRange(const AstShiftR* shiftp) {
m_lsb += VN_AS(shiftp->rhsp(), Const)->toUInt();
}
void limitBitRangeToLsb() { m_msb = std::min(m_msb, m_lsb); }
int wordIdx() const { return m_wordIdx; }
void wordIdx(int i) { m_wordIdx = i; }
bool polarity() const { return m_polarity; }
@ -538,6 +539,7 @@ class ConstBitOpTreeVisitor final : public VNVisitorConst {
Restorer restorer{*this};
incrOps(nodep, __LINE__);
iterateConst(nodep->rhsp());
if (m_leafp) m_leafp->limitBitRangeToLsb();
CONST_BITOP_RETURN_IF(m_failed, nodep->rhsp());
restorer.disableRestore(); // Now all checks passed
} else if (nodep->type() == m_rootp->type()) { // And, Or, Xor

View File

@ -153,6 +153,7 @@ module Test(/*AUTOARG*/
bug4857 i_bug4857(.clk(clk), .in(d), .out(bug4857_out));
bug4864 i_bug4864(.clk(clk), .in(d), .out(bug4864_out));
bug5186 i_bug5186(.clk(clk), .in(d), .out(bug5186_out));
bug5993 i_bug5993(.clk(clk), .in(d[10]));
endmodule
@ -566,3 +567,30 @@ module bug5186(input wire clk, input wire [31:0] in, output out);
result <= bad;
assign out = result;
endmodule
// See issue #5993
// "in4[18]" is just one bit width, so " >> 8'd1" shifts out the bit.
// BitOpTree ignored implicit "& 1". It caused the bug"
module bug5993(input wire clk, input wire in);
reg in3;
reg [23:16] in4;
task automatic checkd(logic gotv, logic expv);
if ((gotv) !== (expv)) begin
$write("%%Error: got=%0d exp=%0d\n", gotv, expv);
$stop;
end
endtask
// verilator lint_off WIDTH
wire wire_2 = in3 ? {4{14'b010111101}} : (in4[18] >> 8'b1);
// verilator lint_on WIDTH
always @(posedge clk) begin
in3 <= '0;
in4 <= in ? 8'b00111__0__10 : 8'b00111__1__10;
checkd(wire_2, 1'b0);
end
endmodule

View File

@ -18,7 +18,7 @@ test.compile(verilator_flags2=["-Wno-UNOPTTHREADS", "--stats", test.pli_filename
test.execute()
if test.vlt:
test.file_grep(test.stats, r'Optimizations, Const bit op reduction\s+(\d+)', 39)
test.file_grep(test.stats, r'Optimizations, Const bit op reduction\s+(\d+)', 43)
test.file_grep(test.stats, r'SplitVar, packed variables split automatically\s+(\d+)', 1)
test.passes()