From 1fc86fd2f13bbc3e16ab2a57a5752936925d3b52 Mon Sep 17 00:00:00 2001 From: Yilou Wang Date: Thu, 4 Dec 2025 13:18:07 +0100 Subject: [PATCH] Fix randomize called within func/task (#6144) (#6753) Co-authored-by: Udaya Raj Subedi <075bei047.udaya@pcampus.edu.np> --- src/V3Width.cpp | 2 ++ test_regress/t/t_randomize_within_func.py | 21 +++++++++++++++ test_regress/t/t_randomize_within_func.v | 32 +++++++++++++++++++++++ 3 files changed, 55 insertions(+) create mode 100755 test_regress/t/t_randomize_within_func.py create mode 100755 test_regress/t/t_randomize_within_func.v diff --git a/src/V3Width.cpp b/src/V3Width.cpp index 77149051b..7ed8dc0cf 100644 --- a/src/V3Width.cpp +++ b/src/V3Width.cpp @@ -6740,6 +6740,8 @@ class WidthVisitor final : public VNVisitor { v3Global.rootp()->typeTablep()->addTypesp(adtypep); withp = methodWithArgument(nodep, false, false, adtypep->findVoidDType(), adtypep->findBitDType(), adtypep); + for (const AstNode* argp = nodep->pinsp(); argp; argp = argp->nextp()) + userIterateAndNext(VN_AS(argp, Arg)->exprp(), WidthVP{SELF, BOTH}.p()); handleRandomizeArgs(nodep, classp); } else if (nodep->name() == "srandom") { nodep->taskp(V3Randomize::newSRandomFunc(m_memberMap, classp)); diff --git a/test_regress/t/t_randomize_within_func.py b/test_regress/t/t_randomize_within_func.py new file mode 100755 index 000000000..466368b3d --- /dev/null +++ b/test_regress/t/t_randomize_within_func.py @@ -0,0 +1,21 @@ +#!/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') + +if not test.have_solver: + test.skip("No constraint solver installed") + +test.compile() + +test.execute() + +test.passes() diff --git a/test_regress/t/t_randomize_within_func.v b/test_regress/t/t_randomize_within_func.v new file mode 100755 index 000000000..e1eb0d2ad --- /dev/null +++ b/test_regress/t/t_randomize_within_func.v @@ -0,0 +1,32 @@ +// DESCRIPTION: Verilator: Test for unsupported multiple global constraints +// This file ONLY is placed under the Creative Commons Public Domain, for +// any use, without warranty, 2025 by PlanV GmbH. +// SPDX-License-Identifier: CC0-1.0 + +class Cls; + rand int m_1; + int m_2; + function void test_this_randomize; + int a; + a = randomize(m_2) with {m_2 > 2 && m_2 < 5;}; + $display("%d: a=%0d %0d", `__LINE__, a, m_2); + if (a != 1) $stop; + // Problem 2 (Fixed): m_2 should be 3 or 4, but get out-of-range return + if (!(m_2 > 2 && m_2 < 5)) $stop; + // Problem 1 (Fixed): Got %Warning: /svaha/wsnyder/SandBox/homecvs/v4/verilator/include/verilated_random.cpp:417: Internal: Solver error: (error "line 9 column 27: invalid empty $ + a = this.randomize() with {m_1 > 5 && m_1 < 10;}; + $display("%d: a=%0d %0d", `__LINE__, a, m_1); + if (a != 1) $stop; + if (!(m_1 > 5 && m_1 < 10)) $stop; + endfunction +endclass + +module t_randomize_within_func; + initial begin + Cls c = new; + c.test_this_randomize(); + + $write("*-* All Finished *-*\n"); + $finish(); + end +endmodule