From ba8e4f9dec5c0891a05c44e2a7c77096143c9fb6 Mon Sep 17 00:00:00 2001 From: JOTEGO Date: Tue, 4 Aug 2026 10:36:25 +0200 Subject: [PATCH] Fix gate deduplication with function arguments (#8038) --- docs/CONTRIBUTORS | 33 ++++++++-------- src/V3Gate.cpp | 6 +-- test_regress/t/t_gate_dedupe_func.py | 19 +++++++++ test_regress/t/t_gate_dedupe_func.v | 59 ++++++++++++++++++++++++++++ 4 files changed, 98 insertions(+), 19 deletions(-) create mode 100755 test_regress/t/t_gate_dedupe_func.py create mode 100644 test_regress/t/t_gate_dedupe_func.v diff --git a/docs/CONTRIBUTORS b/docs/CONTRIBUTORS index 3870edae8..b2f7290f7 100644 --- a/docs/CONTRIBUTORS +++ b/docs/CONTRIBUTORS @@ -7,6 +7,7 @@ contribution terms including the AI policy in ``docs/CONTRIBUTING.rst``. Please see the Verilator manual for 200+ additional contributors. Thanks to all. +24bit-xjkp 404allen404 Adam Bagley Adam Kostrzewski @@ -31,13 +32,14 @@ Andrii Andrieiev anonkey Anthony Donlon Anthony Moore +apocelipes Arkadiusz Kozdra Arthur Rosa Artur Bieniek AUDIY Aylon Chaim Porat -Bartłomiej Chmiel Bartosz Skorowski +Bartłomiej Chmiel Benjamin Collier BRDR LIFE Brian Li @@ -63,24 +65,28 @@ David Ledger David Metz David Stanford David Turner +dependabot[bot] Dercury Diego Roux Dominick Grochowina -Dragon-Git Don Williamson +Dragon-Git Drew Ranck Drew Taussig Driss Hafdi Edgar E. Iglesias +em2machine +emmettifelts Eric Mejdrich Eric Müller Eric Rippey Eryk Szpotański -Eunseo Song Ethan Sifferman +Eunseo Song Eyck Jentzsch Fabian Keßler-Schulz Fan Shupei +february cozzocrea Felix Neumärker Felix Yan Frans Skarman @@ -158,6 +164,7 @@ Josep Sans Joseph Nwabueze Josh Redford Joshua Leahy +JOTEGO (Jose Tejada) Julian Carrier Julian Daube Julie Schwartz @@ -219,6 +226,7 @@ Mladen Slijepcevic Morten Borup Petersen Mostafa Gamal Moubarak Jeje +Muzaffer Kal Nandu Raj Natan Kreimer Nathan Graybeal @@ -274,13 +282,16 @@ Sergey Chusov Sergey Fedorov Sergi Granell Seth Pellegrino +Shashvat Prabhu Shogo Yamazaki Shou-Li Hsu +spomatasmd Srinivasan Venkataramanan Stefan Wallentowitz Stephen Henry Steven Hugg Stuart Morris +sumpster Szymon Gizler Sören Tempel Teng Huang @@ -320,9 +331,11 @@ Wolfgang Mayerwieser Xi Zhang Yan Xu Yangyu Chen +Yilin Li Yilou Wang Yinan Xu Yoda Lee +Yogish Sekhar Yossi Nivin Yu-Sheng Lin Yuri Victorovich @@ -333,18 +346,6 @@ Zhen Yan Zhou Shen Zhouyi Shen Zixi Li -apocelipes -dependabot[bot] -february cozzocrea -sumpster -em2machine -emmettifelts +Zubin Jain Àlex Torregrosa Ícaro Lima -Yogish Sekhar -24bit-xjkp -Zubin Jain -Muzaffer Kal -Yilin Li -Shashvat Prabhu -spomatasmd diff --git a/src/V3Gate.cpp b/src/V3Gate.cpp index b58b6a1f2..5aa74f81e 100644 --- a/src/V3Gate.cpp +++ b/src/V3Gate.cpp @@ -985,9 +985,9 @@ public: if (m_dedupable && m_assignp) { const AstNode* const lhsp = m_assignp->lhsp(); // Possible todo, handle more complex lhs expressions - if (const AstNodeVarRef* const lRefp = VN_CAST(lhsp, NodeVarRef)) { - UASSERT_OBJ(lRefp->varScopep() == consumerVscp, consumerVscp, - "Consumer doesn't match lhs of assign"); + // A logic vertex may also contain a function argument assignment. + const AstNodeVarRef* const lRefp = VN_CAST(lhsp, NodeVarRef); + if (lRefp && lRefp->varScopep() == consumerVscp) { if (const AstNodeAssign* const dup = m_ghash.hashAndFindDupe(m_assignp, activep, m_ifCondp)) { return static_cast(dup->lhsp()); diff --git a/test_regress/t/t_gate_dedupe_func.py b/test_regress/t/t_gate_dedupe_func.py new file mode 100755 index 000000000..00361a3da --- /dev/null +++ b/test_regress/t/t_gate_dedupe_func.py @@ -0,0 +1,19 @@ +#!/usr/bin/env python3 +# DESCRIPTION: Verilator: Gate deduplication with function captures +# +# 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-FileCopyrightText: 2026 Wilson Snyder +# SPDX-License-Identifier: LGPL-3.0-only OR Artistic-2.0 + +import vltest_bootstrap + +test.scenarios('simulator') + +test.compile(verilator_flags2=[ + '--top-module', 'jtcop_game', '-Wno-fatal', '-Wno-IMPLICIT', + '-Wno-WIDTHEXPAND', '-Wno-WIDTHTRUNC', +]) + +test.passes() diff --git a/test_regress/t/t_gate_dedupe_func.v b/test_regress/t/t_gate_dedupe_func.v new file mode 100644 index 000000000..f62595edf --- /dev/null +++ b/test_regress/t/t_gate_dedupe_func.v @@ -0,0 +1,59 @@ +// DESCRIPTION: Verilator: Gate deduplication through function argument +// +// This file ONLY is placed under the Creative Commons Public Domain. +// SPDX-FileCopyrightText: 2026 Jose Tejada +// SPDX-License-Identifier: CC0-1.0 + +module jtcop_bac06( + input rst, + input clk, + input [15:0] cpu_dout, + input [12:1] cpu_addr, + input [1:0] cpu_dsn, + input [7:0] st_addr, + output reg [7:0] st_dout +); + reg [7:0] mode[0:3]; + reg [15:0] hscr, vscr; + reg [3:0] colscr_sh, rowscr_sh; + reg [7:0] def_cfg[0:15]; + + always @(posedge clk) begin + case (st_addr[3:0]) + 0, 1, 2, 3: st_dout <= mode[st_addr[1:0]]; + 4: st_dout <= hscr[7:0]; + 5: st_dout <= hscr[15:8]; + 6: st_dout <= vscr[7:0]; + 7: st_dout <= vscr[15:8]; + 8: st_dout <= {colscr_sh, rowscr_sh}; + default: st_dout <= '0; + endcase + end + + function [15:0] combine(input [15:0] din); + combine = {cpu_dsn[1] ? din[15:8] : cpu_dout[15:8], + cpu_dsn[0] ? din[7:0] : cpu_dout[7:0]}; + endfunction + + always @(posedge clk) begin + if (rst) vscr <= {def_cfg[7], def_cfg[6]}; + else case (cpu_addr[2:1]) + 0: hscr <= combine(hscr); + 1: vscr <= combine(vscr); + 2: colscr_sh <= cpu_dout[3:0]; + 3: rowscr_sh <= cpu_dout[3:0]; + endcase + end +endmodule + +module jtcop_game(input clk, output [7:0] st_dout); + wire [12:1] cpu_addr; + jtcop_main u_main(.cpu_addr(cpu_addr)); + jtcop_bac06 u_ba2(.rst(rst), .clk(clk), .cpu_dout(ba2_din), + .cpu_addr(cpu_addr), .cpu_dsn(ba2_dsn), .st_addr(st_addr), + .st_dout(st_dout)); +endmodule + +module jtcop_main(output [12:1] cpu_addr); + assign cpu_addr = '0; +endmodule