diff --git a/src/V3Ast.cpp b/src/V3Ast.cpp index 8bc1c9ce9..2c66b2da8 100644 --- a/src/V3Ast.cpp +++ b/src/V3Ast.cpp @@ -1078,11 +1078,10 @@ AstNode* AstNode::iterateSubtreeReturnEdits(VNVisitor& v) { } else if (!nodep->backp()) { // Calling on standalone tree; insert a shim node so we can keep // track, then delete it on completion - AstBegin* const tempp = new AstBegin{nodep->fileline(), "[EditWrapper]", nodep}; - { - VL_DO_DANGLING(tempp->stmtsp()->accept(v), - nodep); // nodep to null as may be replaced - } + AstBegin* const tempp + = new AstBegin{nodep->fileline(), "[EditWrapper]", nodep, false, false}; + // nodep to null as may be replaced + VL_DO_DANGLING(tempp->stmtsp()->accept(v), nodep); nodep = tempp->stmtsp()->unlinkFrBackWithNext(); VL_DO_DANGLING(tempp->deleteTree(), tempp); } else { diff --git a/src/V3AstNodeOther.h b/src/V3AstNodeOther.h index 5a30b6452..c22ffcb79 100644 --- a/src/V3AstNodeOther.h +++ b/src/V3AstNodeOther.h @@ -2274,13 +2274,12 @@ class AstBegin final : public AstNodeBlock { // Parents: statement // @astgen op1 := genforp : Optional[AstNode] - bool m_generate : 1; // Underneath a generate + const bool m_generate : 1; // Underneath a generate bool m_needProcess : 1; // Uses VlProcess const bool m_implied : 1; // Not inserted by user public: // Node that puts name into the output stream - AstBegin(FileLine* fl, const string& name, AstNode* stmtsp, bool generate = false, - bool implied = false) + AstBegin(FileLine* fl, const string& name, AstNode* stmtsp, bool generate, bool implied) : ASTGEN_SUPER_Begin(fl, name, stmtsp) , m_generate{generate} , m_needProcess{false} @@ -2289,7 +2288,6 @@ public: void dump(std::ostream& str) const override; void dumpJson(std::ostream& str) const override; bool generate() const { return m_generate; } - void generate(bool flag) { m_generate = flag; } void setNeedProcess() { m_needProcess = true; } bool needProcess() const { return m_needProcess; } bool implied() const { return m_implied; } diff --git a/src/V3AstNodes.cpp b/src/V3AstNodes.cpp index ec7f1d721..82fbbb14b 100644 --- a/src/V3AstNodes.cpp +++ b/src/V3AstNodes.cpp @@ -3256,7 +3256,7 @@ AstAlways* AstAssignW::convertToAlways() { if (hasTimingControl) { // If there's a timing control, put the assignment in a fork..join_none. This process won't // get marked as suspendable and thus will be scheduled normally - AstBegin* const beginp = new AstBegin{flp, "", bodysp}; + AstBegin* const beginp = new AstBegin{flp, "", bodysp, false, false}; AstFork* const forkp = new AstFork{flp, "", beginp}; forkp->joinType(VJoinType::JOIN_NONE); bodysp = forkp; diff --git a/src/V3Begin.cpp b/src/V3Begin.cpp index 4b224a182..33a56aa18 100644 --- a/src/V3Begin.cpp +++ b/src/V3Begin.cpp @@ -125,7 +125,8 @@ class BeginVisitor final : public VNVisitor { // replaced with multiple statements) for (AstNode* stmtp = nodep->stmtsp(); stmtp; stmtp = stmtp->nextp()) { if (!VN_IS(stmtp, Begin)) { - AstBegin* const beginp = new AstBegin{stmtp->fileline(), "", nullptr}; + AstBegin* const beginp + = new AstBegin{stmtp->fileline(), "", nullptr, false, false}; stmtp->replaceWith(beginp); beginp->addStmtsp(stmtp); stmtp = beginp; @@ -430,7 +431,7 @@ AstNode* V3Begin::convertToWhile(AstForeach* nodep) { AstNodeDType* fromDtp = fromp->dtypep()->skipRefp(); // Split into for loop // We record where the body needs to eventually go with bodyPointp - AstNode* bodyPointp = new AstBegin{nodep->fileline(), "[EditWrapper]", nullptr}; + AstNode* bodyPointp = new AstBegin{nodep->fileline(), "[EditWrapper]", nullptr, false, false}; AstNode* newp = nullptr; AstNode* lastp = nodep; AstVar* nestedIndexp = nullptr; diff --git a/src/V3Broken.cpp b/src/V3Broken.cpp index 8df3598e4..765bf7160 100644 --- a/src/V3Broken.cpp +++ b/src/V3Broken.cpp @@ -382,7 +382,7 @@ void V3Broken::allowMidvisitorCheck(bool flag) { s_brokenAllowMidvisitorCheck = void V3Broken::selfTest() { // Exercise addNewed and deleted for coverage, as otherwise only used with VL_LEAK_CHECKS FileLine* const fl = new FileLine{FileLine::commandLineFilename()}; - AstNode* const newp = new AstBegin{fl, "[EditWrapper]", nullptr}; + AstNode* const newp = new AstBegin{fl, "[EditWrapper]", nullptr, false, false}; // Don't actually do it with VL_LEAK_CHECKS, when new/delete calls these. // Otherwise you call addNewed twice on the same address, which is an error. #ifndef VL_LEAK_CHECKS diff --git a/src/V3Fork.cpp b/src/V3Fork.cpp index 88a318b41..9cf4da556 100644 --- a/src/V3Fork.cpp +++ b/src/V3Fork.cpp @@ -470,7 +470,7 @@ class DynScopeVisitor final : public VNVisitor { })) { nodep->user2(true); // Put it in a fork to prevent lifetime issues with the local - AstBegin* const beginp = new AstBegin{nodep->fileline(), "", nullptr}; + AstBegin* const beginp = new AstBegin{nodep->fileline(), "", nullptr, false, false}; AstFork* const forkp = new AstFork{nodep->fileline(), "", beginp}; forkp->joinType(VJoinType::JOIN_NONE); nodep->replaceWith(forkp); diff --git a/src/V3LinkJump.cpp b/src/V3LinkJump.cpp index 39244c091..e552673eb 100644 --- a/src/V3LinkJump.cpp +++ b/src/V3LinkJump.cpp @@ -425,7 +425,7 @@ class LinkJumpVisitor final : public VNVisitor { // Further handling of disable stmt requires all forks to be begin blocks AstBegin* beginp = VN_CAST(forkItemp, Begin); if (!beginp) { - beginp = new AstBegin{fl, "", nullptr}; + beginp = new AstBegin{fl, "", nullptr, false, false}; forkItemp->replaceWith(beginp); beginp->addStmtsp(forkItemp); // In order to continue the iteration diff --git a/src/V3ParseGrammar.cpp b/src/V3ParseGrammar.cpp index 9fa73a99a..51d4821f6 100644 --- a/src/V3ParseGrammar.cpp +++ b/src/V3ParseGrammar.cpp @@ -86,16 +86,13 @@ void V3ParseImp::parserClear() { AstArg* V3ParseGrammar::argWrapList(AstNodeExpr* nodep) { // Convert list of expressions to list of arguments - if (!nodep) return nullptr; AstArg* outp = nullptr; - AstBegin* const tempp = new AstBegin{nodep->fileline(), "[EditWrapper]", nodep}; while (nodep) { AstNodeExpr* const nextp = VN_AS(nodep->nextp(), NodeExpr); - AstNodeExpr* const exprp = nodep->unlinkFrBack(); + if (nextp) nextp->unlinkFrBackWithNext(); + outp = AstNode::addNext(outp, new AstArg{nodep->fileline(), "", nodep}); nodep = nextp; - outp = AstNode::addNext(outp, new AstArg{exprp->fileline(), "", exprp}); } - VL_DO_DANGLING(tempp->deleteTree(), tempp); return outp; } diff --git a/src/V3Randomize.cpp b/src/V3Randomize.cpp index b6a2a027a..327617b44 100644 --- a/src/V3Randomize.cpp +++ b/src/V3Randomize.cpp @@ -597,7 +597,7 @@ class ConstraintExprVisitor final : public VNVisitor { { AstBegin* const tempp - = new AstBegin{fl, "[EditWrapper]", itemsp->unlinkFrBackWithNext()}; + = new AstBegin{fl, "[EditWrapper]", itemsp->unlinkFrBackWithNext(), false, false}; VL_DO_DANGLING(iterateAndNextNull(tempp->stmtsp()), itemsp); itemsp = tempp->stmtsp(); if (itemsp) itemsp->unlinkFrBackWithNext(); @@ -1939,7 +1939,7 @@ class RandomizeVisitor final : public VNVisitor { AstVarRef* const refp = new AstVarRef{fl, classp, memberVarp, VAccess::WRITE}; AstNodeStmt* const stmtp = newRandStmtsp(fl, refp, randcVarp, basicFvarp); if (!refp->backp()) VL_DO_DANGLING(refp->deleteTree(), refp); - basicRandomizep->addStmtsp(new AstBegin{fl, "", stmtp}); + basicRandomizep->addStmtsp(new AstBegin{fl, "", stmtp, false, false}); } }); } diff --git a/src/V3Sched.cpp b/src/V3Sched.cpp index 476d9bfa5..ae1b4fa9b 100644 --- a/src/V3Sched.cpp +++ b/src/V3Sched.cpp @@ -345,7 +345,7 @@ void splitCheck(AstCFunc* ofuncp) { // Unlink all statements, then add item by item to new sub-functions AstBegin* const tempp = new AstBegin{ofuncp->fileline(), "[EditWrapper]", - ofuncp->stmtsp()->unlinkFrBackWithNext()}; + ofuncp->stmtsp()->unlinkFrBackWithNext(), false, false}; // Currently we do not use finalsp in V3Sched, if we do, it needs to be handled here UASSERT_OBJ(!ofuncp->finalsp(), ofuncp, "Should not have any finalps"); while (tempp->stmtsp()) { diff --git a/src/V3SplitVar.cpp b/src/V3SplitVar.cpp index f068c53ba..cb646a942 100644 --- a/src/V3SplitVar.cpp +++ b/src/V3SplitVar.cpp @@ -194,7 +194,7 @@ struct SplitVarImpl VL_NOT_FINAL { stmtp->unlinkFrBack(); // Insert begin-end because temp value may be inserted to this block later. const std::string name = "__VsplitVarBlk" + cvtToStr(modp->user1Inc(1)); - ap->addStmtsp(new AstBegin{ap->fileline(), name, stmtp}); + ap->addStmtsp(new AstBegin{ap->fileline(), name, stmtp, false, false}); } } @@ -204,7 +204,7 @@ struct SplitVarImpl VL_NOT_FINAL { // Insert begin-end because temp value may be inserted to this block later. FileLine* const fl = initp->fileline(); const std::string name = "__VsplitVarBlk" + cvtToStr(modp->user1Inc(1)); - initp->replaceWith(new AstInitial{fl, new AstBegin{fl, name, stmtp}}); + initp->replaceWith(new AstInitial{fl, new AstBegin{fl, name, stmtp, false, false}}); VL_DO_DANGLING(initp->deleteTree(), initp); } } diff --git a/src/V3Task.cpp b/src/V3Task.cpp index a25cd9109..2520c3236 100644 --- a/src/V3Task.cpp +++ b/src/V3Task.cpp @@ -1348,7 +1348,8 @@ class TaskVisitor final : public VNVisitor { AstNode* bodysp = nodep->stmtsp(); if (bodysp) { unlinkAndClone(nodep, bodysp, true); - AstBegin* const tempp = new AstBegin{nodep->fileline(), "[EditWrapper]", bodysp}; + AstBegin* const tempp + = new AstBegin{nodep->fileline(), "[EditWrapper]", bodysp, false, false}; VL_DANGLING(bodysp); // If we cloned due to recursion, now need to rip out the ports // (that remained in place) then got cloned diff --git a/src/V3Timing.cpp b/src/V3Timing.cpp index a016224df..78e827077 100644 --- a/src/V3Timing.cpp +++ b/src/V3Timing.cpp @@ -1029,7 +1029,7 @@ class TimingControlVisitor final : public VNVisitor { } controlp->replaceWith(forkp); AstBegin* beginp = VN_CAST(controlp, Begin); - if (!beginp) beginp = new AstBegin{nodep->fileline(), "", controlp}; + if (!beginp) beginp = new AstBegin{nodep->fileline(), "", controlp, false, false}; forkp->addStmtsp(beginp); controlp = forkp; } diff --git a/src/V3Unroll.cpp b/src/V3Unroll.cpp index b265fe277..f8abcc2cd 100644 --- a/src/V3Unroll.cpp +++ b/src/V3Unroll.cpp @@ -209,7 +209,8 @@ class UnrollVisitor final : public VNVisitor { if (loopValue) { AstConst* varValuep = new AstConst{nodep->fileline(), *loopValue}; // Iteration requires a back, so put under temporary node - AstBegin* tempp = new AstBegin{nodep->fileline(), "[EditWrapper]", clonep}; + AstBegin* tempp + = new AstBegin{nodep->fileline(), "[EditWrapper]", clonep, false, false}; replaceVarRef(tempp->stmtsp(), varValuep); clonep = tempp->stmtsp()->unlinkFrBackWithNext(); VL_DO_CLEAR(tempp->deleteTree(), tempp = nullptr); @@ -302,7 +303,8 @@ class UnrollVisitor final : public VNVisitor { AstNode* clonep = initp->cloneTree(true); AstConst* varValuep = new AstConst{nodep->fileline(), loopValue}; // Iteration requires a back, so put under temporary node - AstBegin* tempp = new AstBegin{nodep->fileline(), "[EditWrapper]", clonep}; + AstBegin* tempp + = new AstBegin{nodep->fileline(), "[EditWrapper]", clonep, false, false}; replaceVarRef(clonep, varValuep); clonep = tempp->stmtsp()->unlinkFrBackWithNext(); VL_DO_CLEAR(tempp->deleteTree(), tempp = nullptr); @@ -327,8 +329,8 @@ class UnrollVisitor final : public VNVisitor { AstConst* varValuep = new AstConst{nodep->fileline(), loopValue}; if (oneloopp) { // Iteration requires a back, so put under temporary node - AstBegin* const tempp - = new AstBegin{oneloopp->fileline(), "[EditWrapper]", oneloopp}; + AstBegin* const tempp = new AstBegin{oneloopp->fileline(), "[EditWrapper]", + oneloopp, false, false}; replaceVarRef(tempp->stmtsp(), varValuep); oneloopp = tempp->stmtsp()->unlinkFrBackWithNext(); VL_DO_DANGLING(tempp->deleteTree(), tempp); @@ -336,7 +338,8 @@ class UnrollVisitor final : public VNVisitor { if (m_generate) { const string index = AstNode::encodeNumber(varValuep->toSInt()); const string nname = m_beginName + "__BRA__" + index + "__KET__"; - oneloopp = new AstBegin{oneloopp->fileline(), nname, oneloopp, true}; + oneloopp + = new AstBegin{oneloopp->fileline(), nname, oneloopp, true, false}; } VL_DO_DANGLING(pushDeletep(varValuep), varValuep); if (newbodysp) { diff --git a/src/V3Width.cpp b/src/V3Width.cpp index 194d4d9fe..4b0915eff 100644 --- a/src/V3Width.cpp +++ b/src/V3Width.cpp @@ -744,7 +744,8 @@ class WidthVisitor final : public VNVisitor { || (!nodep->stmtsp()->nextp() && !nodep->joinType().joinNone())))) { AstNode* stmtsp = nullptr; if (nodep->stmtsp()) stmtsp = nodep->stmtsp()->unlinkFrBack(); - AstBegin* const newp = new AstBegin{nodep->fileline(), nodep->name(), stmtsp}; + AstBegin* const newp + = new AstBegin{nodep->fileline(), nodep->name(), stmtsp, false, false}; nodep->replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } else if (v3Global.opt.timing().isSetTrue()) { diff --git a/src/verilog.y b/src/verilog.y index 810f65ed2..6d4fbea48 100644 --- a/src/verilog.y +++ b/src/verilog.y @@ -3408,9 +3408,9 @@ par_blockPreId: // ==IEEE: par_block but called with leading ID seq_blockFront: // IEEE: part of seq_block yBEGIN - { $$ = new AstBegin{$1, "", nullptr}; } + { $$ = new AstBegin{$1, "", nullptr, false, false}; } | yBEGIN ':' idAny/*new-block_identifier*/ - { $$ = new AstBegin{$3, *$3, nullptr}; } + { $$ = new AstBegin{$3, *$3, nullptr, false, false}; } ; par_blockFront: // IEEE: part of par_block @@ -3422,7 +3422,7 @@ par_blockFront: // IEEE: part of par_block seq_blockFrontPreId: // IEEE: part of seq_block/stmt with leading id id/*block_identifier*/ yP_COLON__BEGIN yBEGIN - { $$ = new AstBegin{$3, *$1, nullptr}; } + { $$ = new AstBegin{$3, *$1, nullptr, false, false}; } ; par_blockFrontPreId: // IEEE: part of par_block/stmt with leading id @@ -3467,7 +3467,7 @@ stmtList: stmt: // IEEE: statement_or_null == function_statement_or_null statement_item { $$ = $1; } // // S05 block creation rule - | id/*block_identifier*/ ':' statement_item { $$ = new AstBegin{$1, *$1, $3}; } + | id/*block_identifier*/ ':' statement_item { $$ = new AstBegin{$1, *$1, $3, false, false}; } // // from _or_null | ';' { $$ = nullptr; } // // labeled par_block/seq_block with leading ':'