diff --git a/Changes b/Changes index b0265165d..dbc9eb50d 100644 --- a/Changes +++ b/Changes @@ -47,9 +47,10 @@ Verilator 5.039 devel * Fix virtual interface member propagation (#6175) (#6184). [Yilou Wang] * Fix `--coverage-expr` null pointer dereference (#6181). [Igor Zaworski, Antmicro Ltd.] * Fix conflicting function/class name linking error (#6182). [Igor Zaworski, Antmicro Ltd.] -* Fix automatic task variables in unrolled loops with forks (#6194) (#6201). [Danny Oler] +* Fix negate of wide structure selections (#6186). * Fix VPI signal range order (#6189) (#6200). [Ibrahim Burak Yorulmaz] * Fix structure select causing 'Wide Op' error (#6191). [Danny Oler] +* Fix automatic task variables in unrolled loops with forks (#6194) (#6201). [Danny Oler] * Fix 'driver same component' assertion (#6211) (#6215). [Geza Lore] * Fix `--stats` overridden by skipping identical build (#6220). [Geza Lore] * Fix MODDUP with duplicate packages to take first package (#6222). diff --git a/src/V3Cast.cpp b/src/V3Cast.cpp index 1cdd43a4d..9795de230 100644 --- a/src/V3Cast.cpp +++ b/src/V3Cast.cpp @@ -173,13 +173,13 @@ class CastVisitor final : public VNVisitor { void visit(AstNegate* nodep) override { iterateChildren(nodep); nodep->user1(nodep->lhsp()->user1()); - if (nodep->lhsp()->widthMin() == 1) { + if (nodep->lhsp()->widthMin() == 1 && !nodep->lhsp()->isWide()) { // We want to avoid a GCC "converting of negative value" warning // from our expansion of // out = {32{a out = - (alhsp(), castSize(nodep)); } else { - ensureCast(nodep->lhsp()); + if (nodep->sizeMattersLhs()) ensureCast(nodep->lhsp()); } } void visit(AstVarRef* nodep) override { @@ -221,6 +221,11 @@ class CastVisitor final : public VNVisitor { void visit(AstMemberSel* nodep) override { iterateChildren(nodep); ensureNullChecked(nodep->fromp()); + nodep->user1(true); + } + void visit(AstStructSel* nodep) override { + iterateChildren(nodep); + nodep->user1(true); } // NOPs diff --git a/test_regress/t/t_struct_negate.py b/test_regress/t/t_struct_negate.py new file mode 100755 index 000000000..f989a35fb --- /dev/null +++ b/test_regress/t/t_struct_negate.py @@ -0,0 +1,18 @@ +#!/usr/bin/env python3 +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2025 by Wilson Snyder. This program is free software; you +# can redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. +# SPDX-License-Identifier: LGPL-3.0-only OR Artistic-2.0 + +import vltest_bootstrap + +test.scenarios('simulator') + +test.compile() + +test.execute() + +test.passes() diff --git a/test_regress/t/t_struct_negate.v b/test_regress/t/t_struct_negate.v new file mode 100644 index 000000000..6803ef09a --- /dev/null +++ b/test_regress/t/t_struct_negate.v @@ -0,0 +1,19 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed under the Creative Commons Public Domain, for +// any use, without warranty, 2025 by Wilson Snyder. +// SPDX-License-Identifier: CC0-1.0 + +module t ( + input logic signed [64:0] i_x, + output logic signed [64:0] o_y +); + struct {logic signed [64:0] m_x;} s; + assign s.m_x = i_x; + assign o_y = -s.m_x; + initial begin + $write("*-* All Finished *-*\n"); + $finish; + end + +endmodule