forked from github/verilator
Support concat assignment to packed array (#3446).
This commit is contained in:
parent
ada58465b2
commit
59dc2853e3
5
Changes
5
Changes
@ -20,10 +20,11 @@ Verilator 4.223 devel
|
||||
* Add -f<optimization> options to replace -O<letter> options (#3436).
|
||||
* Changed --no-merge-const-pool to -fno-merge-const-pool (#3436).
|
||||
* Support compile time trace signal selection with tracing_on/off (#3323). [Shunyao CAD]
|
||||
* Add assert when VerilatedContext is mis-deleted (#3121). [Rupert Swarbrick]
|
||||
* Define VM_TRACE_VCD when tracing in VCD format. [Geza Lore, Shunyao CAD]
|
||||
* Support non-ANSI interface port declarations (#3439). [Geza Lore, Shunyao CAD]
|
||||
* Support concat assignment to packed array (#3446).
|
||||
* Improve conditional merging optimization (#3125). [Geza Lore, Shunyao CAD]
|
||||
* Define VM_TRACE_VCD when tracing in VCD format. [Geza Lore, Shunyao CAD]
|
||||
* Add assert when VerilatedContext is mis-deleted (#3121). [Rupert Swarbrick]
|
||||
* Fix hang with large case statement optimization (#3405). [Mike Urbach]
|
||||
* Fix 'with' operator with type casting (#3387). [xiak95]
|
||||
* Fix incorrect conditional merging (#3409). [Raynard Qiao]
|
||||
|
@ -8538,6 +8538,7 @@ public:
|
||||
AstNodeDType* childDTypep() const { return VN_AS(op1p(), NodeDType); }
|
||||
void childDTypep(AstNodeDType* nodep) { setOp1p(nodep); }
|
||||
AstNode* itemsp() const { return op2p(); } // op2 = AstPatReplicate, AstPatMember, etc
|
||||
void addItemsp(AstNode* nodep) { addOp2p(nodep); }
|
||||
};
|
||||
class AstPatMember final : public AstNodeMath {
|
||||
// Verilog '{a} or '{a{b}}
|
||||
|
@ -504,6 +504,7 @@ private:
|
||||
// width: LHS + RHS
|
||||
AstNodeDType* const vdtypep = m_vup->dtypeNullSkipRefp();
|
||||
userIterate(vdtypep, WidthVP(SELF, BOTH).p());
|
||||
// Conversions
|
||||
if (VN_IS(vdtypep, QueueDType)) {
|
||||
// Queue "element 0" is lhsp, so we need to swap arguments
|
||||
auto* const newp = new AstConsQueue(nodep->fileline(), nodep->rhsp()->unlinkFrBack(),
|
||||
@ -521,6 +522,16 @@ private:
|
||||
userIterateChildren(newp, m_vup);
|
||||
return;
|
||||
}
|
||||
if (VN_IS(vdtypep, UnpackArrayDType)) {
|
||||
auto* const newp = new AstPattern{nodep->fileline(), nullptr};
|
||||
patConcatConvertRecurse(newp, nodep);
|
||||
nodep->replaceWith(newp);
|
||||
VL_DO_DANGLING(pushDeletep(nodep), nodep);
|
||||
userIterate(newp, m_vup);
|
||||
return;
|
||||
}
|
||||
|
||||
// Concat handling
|
||||
if (m_vup->prelim()) {
|
||||
if (VN_IS(vdtypep, AssocArrayDType) //
|
||||
|| VN_IS(vdtypep, DynArrayDType) //
|
||||
@ -662,7 +673,8 @@ private:
|
||||
}
|
||||
|
||||
AstNodeDType* const vdtypep = m_vup->dtypeNullSkipRefp();
|
||||
if (VN_IS(vdtypep, QueueDType) || VN_IS(vdtypep, DynArrayDType)) {
|
||||
if (VN_IS(vdtypep, QueueDType) || VN_IS(vdtypep, DynArrayDType)
|
||||
|| VN_IS(vdtypep, UnpackArrayDType)) {
|
||||
if (times != 1)
|
||||
nodep->v3warn(E_UNSUPPORTED, "Unsupported: Non-1 replication to form "
|
||||
<< vdtypep->prettyDTypeNameQ()
|
||||
@ -674,7 +686,7 @@ private:
|
||||
VL_DO_DANGLING(pushDeletep(nodep), nodep);
|
||||
return;
|
||||
}
|
||||
if (VN_IS(vdtypep, AssocArrayDType) || VN_IS(vdtypep, UnpackArrayDType)) {
|
||||
if (VN_IS(vdtypep, AssocArrayDType)) {
|
||||
nodep->v3warn(E_UNSUPPORTED, "Unsupported: Replication to form "
|
||||
<< vdtypep->prettyDTypeNameQ() << " data type");
|
||||
}
|
||||
@ -6231,6 +6243,21 @@ private:
|
||||
return patmap;
|
||||
}
|
||||
|
||||
void patConcatConvertRecurse(AstPattern* patternp, AstConcat* nodep) {
|
||||
if (AstConcat* lhsp = VN_CAST(nodep->lhsp(), Concat)) {
|
||||
patConcatConvertRecurse(patternp, lhsp);
|
||||
} else {
|
||||
patternp->addItemsp(new AstPatMember{nodep->lhsp()->fileline(),
|
||||
nodep->lhsp()->unlinkFrBack(), nullptr, nullptr});
|
||||
}
|
||||
if (AstConcat* rhsp = VN_CAST(nodep->rhsp(), Concat)) {
|
||||
patConcatConvertRecurse(patternp, rhsp);
|
||||
} else {
|
||||
patternp->addItemsp(new AstPatMember{nodep->rhsp()->fileline(),
|
||||
nodep->rhsp()->unlinkFrBack(), nullptr, nullptr});
|
||||
}
|
||||
}
|
||||
|
||||
void makeOpenArrayShell(AstNodeFTaskRef* nodep) {
|
||||
UINFO(4, "Replicate openarray function " << nodep->taskp() << endl);
|
||||
AstNodeFTask* const oldTaskp = nodep->taskp();
|
||||
|
21
test_regress/t/t_concat_unpack.pl
Executable file
21
test_regress/t/t_concat_unpack.pl
Executable file
@ -0,0 +1,21 @@
|
||||
#!/usr/bin/env perl
|
||||
if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; }
|
||||
# DESCRIPTION: Verilator: Verilog Test driver/expect definition
|
||||
#
|
||||
# Copyright 2022 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
|
||||
|
||||
scenarios(simulator => 1);
|
||||
|
||||
compile(
|
||||
);
|
||||
|
||||
execute(
|
||||
check_finished => 1,
|
||||
);
|
||||
|
||||
ok(1);
|
||||
1;
|
36
test_regress/t/t_concat_unpack.v
Executable file
36
test_regress/t/t_concat_unpack.v
Executable file
@ -0,0 +1,36 @@
|
||||
// DESCRIPTION: Verilator: Verilog Test module
|
||||
//
|
||||
// This file ONLY is placed under the Creative Commons Public Domain, for
|
||||
// any use, without warranty, 2022 by Wilson Snyder.
|
||||
// SPDX-License-Identifier: CC0-1.0
|
||||
|
||||
module t(/*AUTOARG*/
|
||||
// Inputs
|
||||
clk
|
||||
);
|
||||
input clk;
|
||||
|
||||
wire [31:0] arr [0:7];
|
||||
assign arr[0:7] = {
|
||||
{16'hffff, 16'h0000},
|
||||
{16'h0000, 16'h0000},
|
||||
{16'h0a0a, 16'h0000},
|
||||
{16'ha0a0, 16'h0000},
|
||||
{16'hffff, 16'h0000},
|
||||
{16'h0000, 16'h0000},
|
||||
{16'h0a0a, 16'h0000},
|
||||
{16'ha0a0, 16'h0000}
|
||||
};
|
||||
|
||||
int cyc = 0;
|
||||
|
||||
always @(posedge clk) begin
|
||||
cyc <= cyc + 1;
|
||||
if (cyc == 9) begin
|
||||
if (arr[0] !== 32'hffff0000) $stop;
|
||||
if (arr[7] !== 32'ha0a00000) $stop;
|
||||
$write("*-* All Finished *-*\n");
|
||||
$finish;
|
||||
end
|
||||
end
|
||||
endmodule
|
@ -1,23 +1,6 @@
|
||||
%Error-UNSUPPORTED: t/t_unpacked_concat_bad.v:17:46: Unsupported: Replication to form 'bit[31:0]$[1:0]' data type
|
||||
%Error-UNSUPPORTED: t/t_unpacked_concat_bad.v:17:46: Unsupported: Non-1 replication to form 'bit[31:0]$[1:0]' data type
|
||||
: ... In instance t
|
||||
17 | localparam bit_int_t count_bits [1:0] = {2{$bits(count_t)}};
|
||||
| ^
|
||||
... For error description see https://verilator.org/warn/UNSUPPORTED?v=latest
|
||||
%Warning-WIDTHCONCAT: t/t_unpacked_concat_bad.v:17:47: Unsized numbers/parameters not allowed in replications.
|
||||
: ... In instance t
|
||||
17 | localparam bit_int_t count_bits [1:0] = {2{$bits(count_t)}};
|
||||
| ^~~~~
|
||||
... Use "/* verilator lint_off WIDTHCONCAT */" and lint_on around source to disable this message.
|
||||
%Error-UNSUPPORTED: t/t_unpacked_concat_bad.v:18:45: Unsupported: Replication to form 'bit[31:0]$[1:0]' data type
|
||||
: ... In instance t
|
||||
18 | localparam bit_int_t count_bitsc [1:0] = {$bits(count_t), $bits(count_t)};
|
||||
| ^
|
||||
%Warning-WIDTHCONCAT: t/t_unpacked_concat_bad.v:18:46: Unsized numbers/parameters not allowed in concatenations.
|
||||
: ... In instance t
|
||||
18 | localparam bit_int_t count_bitsc [1:0] = {$bits(count_t), $bits(count_t)};
|
||||
| ^~~~~
|
||||
%Warning-WIDTHCONCAT: t/t_unpacked_concat_bad.v:18:60: Unsized numbers/parameters not allowed in replications.
|
||||
: ... In instance t
|
||||
18 | localparam bit_int_t count_bitsc [1:0] = {$bits(count_t), $bits(count_t)};
|
||||
| ^
|
||||
%Error: Exiting due to
|
||||
|
Loading…
Reference in New Issue
Block a user