mirror of
https://github.com/verilator/verilator.git
synced 2025-01-01 04:07:34 +00:00
Support ++/-- on dotted member variables.
This commit is contained in:
parent
827cbf22c9
commit
d67d75282c
1
Changes
1
Changes
@ -22,6 +22,7 @@ Verilator 5.009 devel
|
||||
* Support method calls without parenthesis (#4034). [Ryszard Rozak, Antmicro Ltd]
|
||||
* Support complicated IEEE 'for' assignments.
|
||||
* Support $fopen as an expression.
|
||||
* Support ++/-- on dotted member variables.
|
||||
* Change range order warning from LITENDIAN to ASCRANGE (#4010). [Iztok Jeras]
|
||||
* Change ZERODLY to a warning.
|
||||
* Fix random internal crashes (#666). [Dag Lem]
|
||||
|
@ -240,11 +240,12 @@ private:
|
||||
return;
|
||||
}
|
||||
|
||||
const AstNodeVarRef* varrefp = nullptr;
|
||||
if (m_unsupportedHere || !(varrefp = VN_CAST(nodep->rhsp(), VarRef))) {
|
||||
if (m_unsupportedHere) {
|
||||
nodep->v3warn(E_UNSUPPORTED, "Unsupported: Incrementation in this context.");
|
||||
return;
|
||||
}
|
||||
AstNodeExpr* const readp = nodep->rhsp();
|
||||
AstNodeExpr* const writep = nodep->thsp();
|
||||
|
||||
AstConst* const constp = VN_AS(nodep->lhsp(), Const);
|
||||
UASSERT_OBJ(nodep, constp, "Expecting CONST");
|
||||
@ -254,8 +255,9 @@ private:
|
||||
// Prepare a temporary variable
|
||||
FileLine* const fl = backp->fileline();
|
||||
const string name = string{"__Vincrement"} + cvtToStr(++m_modIncrementsNum);
|
||||
AstVar* const varp = new AstVar{fl, VVarType::BLOCKTEMP, name, VFlagChildDType{},
|
||||
varrefp->varp()->subDTypep()->cloneTree(true)};
|
||||
AstVar* const varp = new AstVar{
|
||||
fl, VVarType::BLOCKTEMP, name, VFlagChildDType{},
|
||||
new AstRefDType{fl, AstRefDType::FlagTypeOfExpr{}, readp->cloneTree(true)}};
|
||||
if (m_ftaskp) varp->funcLocal(true);
|
||||
|
||||
// Declare the variable
|
||||
@ -264,30 +266,29 @@ private:
|
||||
// Define what operation will we be doing
|
||||
AstNodeExpr* operp;
|
||||
if (VN_IS(nodep, PostSub) || VN_IS(nodep, PreSub)) {
|
||||
operp = new AstSub{fl, new AstVarRef{fl, varrefp->varp(), VAccess::READ}, newconstp};
|
||||
operp = new AstSub{fl, readp->cloneTree(true), newconstp};
|
||||
} else {
|
||||
operp = new AstAdd{fl, new AstVarRef{fl, varrefp->varp(), VAccess::READ}, newconstp};
|
||||
operp = new AstAdd{fl, readp->cloneTree(true), newconstp};
|
||||
}
|
||||
|
||||
if (VN_IS(nodep, PreAdd) || VN_IS(nodep, PreSub)) {
|
||||
// PreAdd/PreSub operations
|
||||
// Immediately after declaration - increment it by one
|
||||
varp->addNextHere(new AstAssign{fl, new AstVarRef{fl, varrefp->varp(), VAccess::WRITE},
|
||||
varp->addNextHere(new AstAssign{fl, writep->cloneTree(true),
|
||||
new AstVarRef{fl, varp, VAccess::READ}});
|
||||
// Immediately after incrementing - assign it to the original variable
|
||||
varp->addNextHere(new AstAssign{fl, new AstVarRef{fl, varp, VAccess::WRITE}, operp});
|
||||
} else {
|
||||
// PostAdd/PostSub operations
|
||||
// assign the original variable to the temporary one
|
||||
varp->addNextHere(
|
||||
new AstAssign{fl, new AstVarRef{fl, varrefp->varp(), VAccess::WRITE}, operp});
|
||||
varp->addNextHere(new AstAssign{fl, writep->cloneTree(true), operp});
|
||||
// Increment the original variable by one
|
||||
varp->addNextHere(new AstAssign{fl, new AstVarRef{fl, varp, VAccess::WRITE},
|
||||
new AstVarRef{fl, varrefp->varp(), VAccess::READ}});
|
||||
readp->cloneTree(true)});
|
||||
}
|
||||
|
||||
// Replace the node with the temporary
|
||||
nodep->replaceWith(new AstVarRef{varrefp->fileline(), varp, VAccess::READ});
|
||||
nodep->replaceWith(new AstVarRef{readp->fileline(), varp, VAccess::READ});
|
||||
VL_DO_DANGLING(nodep->deleteTree(), nodep);
|
||||
}
|
||||
void visit(AstPreAdd* nodep) override { prepost_visit(nodep); }
|
||||
|
21
test_regress/t/t_class_inc.pl
Executable file
21
test_regress/t/t_class_inc.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 2023 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;
|
37
test_regress/t/t_class_inc.v
Normal file
37
test_regress/t/t_class_inc.v
Normal file
@ -0,0 +1,37 @@
|
||||
// DESCRIPTION: Verilator: Verilog Test module
|
||||
//
|
||||
// This file ONLY is placed under the Creative Commons Public Domain, for
|
||||
// any use, without warranty, 2023 by Wilson Snyder.
|
||||
// SPDX-License-Identifier: CC0-1.0
|
||||
|
||||
class Base #(type T = integer);
|
||||
T m_count;
|
||||
|
||||
function void test1();
|
||||
if (this.m_count != 0) $stop;
|
||||
if (this.m_count++ != 0) $stop;
|
||||
if (this.m_count != 1) $stop;
|
||||
if (m_count++ != 1) $stop;
|
||||
if (this.m_count != 2) $stop;
|
||||
endfunction
|
||||
endclass
|
||||
|
||||
class Cls #(type T = integer) extends Base #(T);
|
||||
endclass
|
||||
|
||||
module t;
|
||||
Cls #(int) c;
|
||||
|
||||
initial begin
|
||||
c = new;
|
||||
c.test1();
|
||||
|
||||
c.m_count = 0;
|
||||
if (c.m_count != 0) $stop;
|
||||
if (c.m_count++ != 0) $stop;
|
||||
if (c.m_count != 1) $stop;
|
||||
|
||||
$write("*-* All Finished *-*\n");
|
||||
$finish;
|
||||
end
|
||||
endmodule
|
@ -17,9 +17,6 @@
|
||||
%Error-UNSUPPORTED: t/t_increment_bad.v:27:29: Unsupported: Incrementation in this context.
|
||||
27 | pos = (a > 0) ? a++ : --b;
|
||||
| ^~
|
||||
%Error-UNSUPPORTED: t/t_increment_bad.v:29:24: Unsupported: Incrementation in this context.
|
||||
29 | pos = array[0][0]++;
|
||||
| ^~
|
||||
%Error-UNSUPPORTED: t/t_increment_bad.v:32:37: Unsupported: Incrementation in this context.
|
||||
32 | assert property (@(posedge clk) a++ >= 0);
|
||||
| ^~
|
||||
|
@ -138,6 +138,16 @@ module t (/*AUTOARG*/
|
||||
r = real'(96'shf0000000_00000000_00000000);
|
||||
if (r != -4951760157141521099596496896.0) $stop;
|
||||
|
||||
r = 1.5;
|
||||
if (r++ != 1.5) $stop;
|
||||
if (r != 2.5) $stop;
|
||||
if (r-- != 2.5) $stop;
|
||||
if (r != 1.5) $stop;
|
||||
if (++r != 2.5) $stop;
|
||||
if (r != 2.5) $stop;
|
||||
if (--r != 1.5) $stop;
|
||||
if (r != 1.5) $stop;
|
||||
|
||||
r = 1.23456;
|
||||
s = $sformatf("%g", r);
|
||||
`checks(s, "1.23456");
|
||||
|
21
test_regress/t/t_math_wide_inc.pl
Executable file
21
test_regress/t/t_math_wide_inc.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 2003 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;
|
89
test_regress/t/t_math_wide_inc.v
Normal file
89
test_regress/t/t_math_wide_inc.v
Normal file
@ -0,0 +1,89 @@
|
||||
// DESCRIPTION: Verilator: Verilog Test module
|
||||
//
|
||||
// Copyright 2023 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
|
||||
|
||||
module t (/*AUTOARG*/
|
||||
// Inputs
|
||||
clk
|
||||
);
|
||||
input clk;
|
||||
|
||||
integer i;
|
||||
reg [6:0] w7;
|
||||
reg [14:0] w15;
|
||||
reg [30:0] w31;
|
||||
reg [62:0] w63;
|
||||
reg [94:0] w95;
|
||||
|
||||
integer cyc = 0;
|
||||
|
||||
// Test loop
|
||||
always @ (posedge clk) begin
|
||||
`ifdef TEST_VERBOSE
|
||||
$write("[%0t] cyc==%0d\n", $time, cyc);
|
||||
`endif
|
||||
cyc <= cyc + 1;
|
||||
if (cyc==0) begin
|
||||
// Setup
|
||||
w7 = {7{1'b1}};
|
||||
w15 = {15{1'b1}};
|
||||
w31 = {31{1'b1}};
|
||||
w63 = {63{1'b1}};
|
||||
w95 = {95{1'b1}};
|
||||
end
|
||||
else if (cyc == 1) begin
|
||||
if (w7++ != {7{1'b1}}) $stop;
|
||||
if (w7 != {7{1'b0}}) $stop;
|
||||
if (w7-- != {7{1'b0}}) $stop;
|
||||
if (w7 != {7{1'b1}}) $stop;
|
||||
if (++w7 != {7{1'b0}}) $stop;
|
||||
if (w7 != {7{1'b0}}) $stop;
|
||||
if (--w7 != {7{1'b1}}) $stop;
|
||||
if (w7 != {7{1'b1}}) $stop;
|
||||
|
||||
if (w15++ != {15{1'b1}}) $stop;
|
||||
if (w15 != {15{1'b0}}) $stop;
|
||||
if (w15-- != {15{1'b0}}) $stop;
|
||||
if (w15 != {15{1'b1}}) $stop;
|
||||
if (++w15 != {15{1'b0}}) $stop;
|
||||
if (w15 != {15{1'b0}}) $stop;
|
||||
if (--w15 != {15{1'b1}}) $stop;
|
||||
if (w15 != {15{1'b1}}) $stop;
|
||||
|
||||
if (w31++ != {31{1'b1}}) $stop;
|
||||
if (w31 != {31{1'b0}}) $stop;
|
||||
if (w31-- != {31{1'b0}}) $stop;
|
||||
if (w31 != {31{1'b1}}) $stop;
|
||||
if (++w31 != {31{1'b0}}) $stop;
|
||||
if (w31 != {31{1'b0}}) $stop;
|
||||
if (--w31 != {31{1'b1}}) $stop;
|
||||
if (w31 != {31{1'b1}}) $stop;
|
||||
|
||||
if (w63++ != {63{1'b1}}) $stop;
|
||||
if (w63 != {63{1'b0}}) $stop;
|
||||
if (w63-- != {63{1'b0}}) $stop;
|
||||
if (w63 != {63{1'b1}}) $stop;
|
||||
if (++w63 != {63{1'b0}}) $stop;
|
||||
if (w63 != {63{1'b0}}) $stop;
|
||||
if (--w63 != {63{1'b1}}) $stop;
|
||||
if (w63 != {63{1'b1}}) $stop;
|
||||
|
||||
if (w95++ != {95{1'b1}}) $stop;
|
||||
if (w95 != {95{1'b0}}) $stop;
|
||||
if (w95-- != {95{1'b0}}) $stop;
|
||||
if (w95 != {95{1'b1}}) $stop;
|
||||
if (++w95 != {95{1'b0}}) $stop;
|
||||
if (w95 != {95{1'b0}}) $stop;
|
||||
if (--w95 != {95{1'b1}}) $stop;
|
||||
if (w95 != {95{1'b1}}) $stop;
|
||||
end
|
||||
else if (cyc==99) begin
|
||||
$write("*-* All Finished *-*\n");
|
||||
$finish;
|
||||
end
|
||||
end
|
||||
endmodule
|
Loading…
Reference in New Issue
Block a user