Internals: Fix constructor style.

This commit is contained in:
Wilson Snyder 2022-11-20 17:40:38 -05:00
parent 25f970eac2
commit f44cd9cd48
10 changed files with 373 additions and 374 deletions

View File

@ -176,10 +176,10 @@ private:
if (neverItem(nodep, iconstp)) { if (neverItem(nodep, iconstp)) {
// X in casez can't ever be executed // X in casez can't ever be executed
} else { } else {
V3Number nummask(itemp, iconstp->width()); V3Number nummask{itemp, iconstp->width()};
nummask.opBitsNonX(iconstp->num()); nummask.opBitsNonX(iconstp->num());
const uint32_t mask = nummask.toUInt(); const uint32_t mask = nummask.toUInt();
V3Number numval(itemp, iconstp->width()); V3Number numval{itemp, iconstp->width()};
numval.opBitsOne(iconstp->num()); numval.opBitsOne(iconstp->num());
const uint32_t val = numval.toUInt(); const uint32_t val = numval.toUInt();
@ -291,10 +291,10 @@ private:
// AstNode* and1p = new AstAnd(cexprp->fileline(), cexprp->cloneTree(false), // AstNode* and1p = new AstAnd(cexprp->fileline(), cexprp->cloneTree(false),
// new AstConst(cexprp->fileline(), nummask)); // new AstConst(cexprp->fileline(), nummask));
AstNodeExpr* const and1p AstNodeExpr* const and1p
= new AstSel(cexprp->fileline(), cexprp->cloneTree(false), msb, 1); = new AstSel{cexprp->fileline(), cexprp->cloneTree(false), msb, 1};
AstNodeExpr* const eqp AstNodeExpr* const eqp
= new AstNeq(cexprp->fileline(), new AstConst(cexprp->fileline(), 0), and1p); = new AstNeq{cexprp->fileline(), new AstConst{cexprp->fileline(), 0}, and1p};
AstIf* const ifp = new AstIf(cexprp->fileline(), eqp, tree1p, tree0p); AstIf* const ifp = new AstIf{cexprp->fileline(), eqp, tree1p, tree0p};
ifp->user3(1); // So we don't bother to clone it ifp->user3(1); // So we don't bother to clone it
return ifp; return ifp;
} }
@ -346,7 +346,7 @@ private:
itemp = VN_AS(itemp->nextp(), CaseItem)) { itemp = VN_AS(itemp->nextp(), CaseItem)) {
if (!itemp->condsp()) { if (!itemp->condsp()) {
// Default clause. Just make true, we'll optimize it away later // Default clause. Just make true, we'll optimize it away later
itemp->addCondsp(new AstConst(itemp->fileline(), AstConst::BitTrue())); itemp->addCondsp(new AstConst{itemp->fileline(), AstConst::BitTrue{}});
hadDefault = true; hadDefault = true;
} else { } else {
// Expressioned clause // Expressioned clause
@ -364,23 +364,23 @@ private:
VL_DANGLING(iconstp); VL_DANGLING(iconstp);
// For simplicity, make expression that is not equal, and let later // For simplicity, make expression that is not equal, and let later
// optimizations remove it // optimizations remove it
condp = new AstConst(itemp->fileline(), AstConst::BitFalse()); condp = new AstConst{itemp->fileline(), AstConst::BitFalse{}};
} else if (AstInsideRange* const irangep = VN_CAST(icondp, InsideRange)) { } else if (AstInsideRange* const irangep = VN_CAST(icondp, InsideRange)) {
// Similar logic in V3Width::visit(AstInside) // Similar logic in V3Width::visit(AstInside)
condp = irangep->newAndFromInside(cexprp, irangep->lhsp()->unlinkFrBack(), condp = irangep->newAndFromInside(cexprp, irangep->lhsp()->unlinkFrBack(),
irangep->rhsp()->unlinkFrBack()); irangep->rhsp()->unlinkFrBack());
} else if (iconstp && iconstp->num().isFourState() } else if (iconstp && iconstp->num().isFourState()
&& (nodep->casex() || nodep->casez() || nodep->caseInside())) { && (nodep->casex() || nodep->casez() || nodep->caseInside())) {
V3Number nummask(itemp, iconstp->width()); V3Number nummask{itemp, iconstp->width()};
nummask.opBitsNonX(iconstp->num()); nummask.opBitsNonX(iconstp->num());
V3Number numval(itemp, iconstp->width()); V3Number numval{itemp, iconstp->width()};
numval.opBitsOne(iconstp->num()); numval.opBitsOne(iconstp->num());
AstNodeExpr* const and1p AstNodeExpr* const and1p
= new AstAnd(itemp->fileline(), cexprp->cloneTree(false), = new AstAnd{itemp->fileline(), cexprp->cloneTree(false),
new AstConst(itemp->fileline(), nummask)); new AstConst{itemp->fileline(), nummask}};
AstNodeExpr* const and2p = new AstAnd( AstNodeExpr* const and2p = new AstAnd{
itemp->fileline(), new AstConst(itemp->fileline(), numval), itemp->fileline(), new AstConst{itemp->fileline(), numval},
new AstConst(itemp->fileline(), nummask)); new AstConst{itemp->fileline(), nummask}};
VL_DO_DANGLING(icondp->deleteTree(), icondp); VL_DO_DANGLING(icondp->deleteTree(), icondp);
VL_DANGLING(iconstp); VL_DANGLING(iconstp);
condp = AstEq::newTyped(itemp->fileline(), and1p, and2p); condp = AstEq::newTyped(itemp->fileline(), and1p, and2p);
@ -393,7 +393,7 @@ private:
if (!ifexprp) { if (!ifexprp) {
ifexprp = condp; ifexprp = condp;
} else { } else {
ifexprp = new AstLogOr(itemp->fileline(), ifexprp, condp); ifexprp = new AstLogOr{itemp->fileline(), ifexprp, condp};
} }
} }
// Replace expression in tree // Replace expression in tree
@ -404,8 +404,8 @@ private:
if (!hadDefault) { if (!hadDefault) {
// If there was no default, add a empty one, this greatly simplifies below code // If there was no default, add a empty one, this greatly simplifies below code
// and constant propagation will just eliminate it for us later. // and constant propagation will just eliminate it for us later.
nodep->addItemsp(new AstCaseItem( nodep->addItemsp(new AstCaseItem{
nodep->fileline(), new AstConst(nodep->fileline(), AstConst::BitTrue()), nullptr)); nodep->fileline(), new AstConst{nodep->fileline(), AstConst::BitTrue{}}, nullptr});
} }
if (debug() >= 9) nodep->dumpTree(cout, " _comp_COND: "); if (debug() >= 9) nodep->dumpTree(cout, " _comp_COND: ");
// Now build the IF statement tree // Now build the IF statement tree
@ -428,7 +428,7 @@ private:
if (++depth > CASE_ENCODER_GROUP_DEPTH) depth = 1; if (++depth > CASE_ENCODER_GROUP_DEPTH) depth = 1;
if (depth == 1) { // First group or starting new group if (depth == 1) { // First group or starting new group
itemnextp = nullptr; itemnextp = nullptr;
AstIf* const newp = new AstIf(itemp->fileline(), ifexprp->cloneTree(true)); AstIf* const newp = new AstIf{itemp->fileline(), ifexprp->cloneTree(true)};
if (groupnextp) { if (groupnextp) {
groupnextp->addElsesp(newp); groupnextp->addElsesp(newp);
} else { } else {
@ -438,7 +438,7 @@ private:
} else { // Continue group, modify if condition to OR in this new condition } else { // Continue group, modify if condition to OR in this new condition
AstNodeExpr* const condp = groupnextp->condp()->unlinkFrBack(); AstNodeExpr* const condp = groupnextp->condp()->unlinkFrBack();
groupnextp->condp( groupnextp->condp(
new AstOr(ifexprp->fileline(), condp, ifexprp->cloneTree(true))); new AstOr{ifexprp->fileline(), condp, ifexprp->cloneTree(true)});
} }
} }
{ // Make the new lower IF and attach in the tree { // Make the new lower IF and attach in the tree
@ -446,9 +446,9 @@ private:
VL_DANGLING(ifexprp); VL_DANGLING(ifexprp);
if (depth == CASE_ENCODER_GROUP_DEPTH) { // End of group - can skip the condition if (depth == CASE_ENCODER_GROUP_DEPTH) { // End of group - can skip the condition
VL_DO_DANGLING(itemexprp->deleteTree(), itemexprp); VL_DO_DANGLING(itemexprp->deleteTree(), itemexprp);
itemexprp = new AstConst(itemp->fileline(), AstConst::BitTrue()); itemexprp = new AstConst{itemp->fileline(), AstConst::BitTrue{}};
} }
AstIf* const newp = new AstIf(itemp->fileline(), itemexprp, istmtsp); AstIf* const newp = new AstIf{itemp->fileline(), itemexprp, istmtsp};
if (itemnextp) { if (itemnextp) {
itemnextp->addElsesp(newp); itemnextp->addElsesp(newp);
} else { } else {

View File

@ -156,28 +156,28 @@ private:
varp = it->second; varp = it->second;
} else { } else {
if (newdtypep) { if (newdtypep) {
varp = new AstVar(oldvarscp->fileline(), VVarType::BLOCKTEMP, name, newdtypep); varp = new AstVar{oldvarscp->fileline(), VVarType::BLOCKTEMP, name, newdtypep};
} else if (width == 0) { } else if (width == 0) {
varp = new AstVar(oldvarscp->fileline(), VVarType::BLOCKTEMP, name, varp = new AstVar{oldvarscp->fileline(), VVarType::BLOCKTEMP, name,
oldvarscp->varp()); oldvarscp->varp()};
varp->dtypeFrom(oldvarscp); varp->dtypeFrom(oldvarscp);
} else { // Used for vset and dimensions, so can zero init } else { // Used for vset and dimensions, so can zero init
varp = new AstVar(oldvarscp->fileline(), VVarType::BLOCKTEMP, name, varp = new AstVar{oldvarscp->fileline(), VVarType::BLOCKTEMP, name,
VFlagBitPacked(), width); VFlagBitPacked{}, width};
} }
addmodp->addStmtsp(varp); addmodp->addStmtsp(varp);
m_modVarMap.emplace(std::make_pair(addmodp, name), varp); m_modVarMap.emplace(std::make_pair(addmodp, name), varp);
} }
AstVarScope* const varscp AstVarScope* const varscp
= new AstVarScope(oldvarscp->fileline(), oldvarscp->scopep(), varp); = new AstVarScope{oldvarscp->fileline(), oldvarscp->scopep(), varp};
oldvarscp->scopep()->addVarsp(varscp); oldvarscp->scopep()->addVarsp(varscp);
return varscp; return varscp;
} }
AstActive* createActive(AstNode* varrefp) { AstActive* createActive(AstNode* varrefp) {
AstActive* const newactp AstActive* const newactp
= new AstActive(varrefp->fileline(), "sequentdly", m_activep->sensesp()); = new AstActive{varrefp->fileline(), "sequentdly", m_activep->sensesp()};
// Was addNext(), but addNextHere() avoids a linear search. // Was addNext(), but addNextHere() avoids a linear search.
m_activep->addNextHere(newactp); m_activep->addNextHere(newactp);
return newactp; return newactp;
@ -204,7 +204,7 @@ private:
// Make a new sensitivity list, which is the combination of both blocks // Make a new sensitivity list, which is the combination of both blocks
AstSenItem* const sena = m_activep->sensesp()->sensesp()->cloneTree(true); AstSenItem* const sena = m_activep->sensesp()->sensesp()->cloneTree(true);
AstSenItem* const senb = oldactivep->sensesp()->sensesp()->cloneTree(true); AstSenItem* const senb = oldactivep->sensesp()->sensesp()->cloneTree(true);
AstSenTree* const treep = new AstSenTree(m_activep->fileline(), sena); AstSenTree* const treep = new AstSenTree{m_activep->fileline(), sena};
if (senb) treep->addSensesp(senb); if (senb) treep->addSensesp(senb);
if (AstSenTree* const storep = oldactivep->sensesStorep()) { if (AstSenTree* const storep = oldactivep->sensesStorep()) {
storep->unlinkFrBack(); storep->unlinkFrBack();
@ -265,11 +265,11 @@ private:
+ oldvarp->shortName() + "__v" + cvtToStr(modVecNum)); + oldvarp->shortName() + "__v" + cvtToStr(modVecNum));
AstVarScope* const bitvscp AstVarScope* const bitvscp
= createVarSc(varrefp->varScopep(), bitvarname, dimp->width(), nullptr); = createVarSc(varrefp->varScopep(), bitvarname, dimp->width(), nullptr);
AstAssign* const bitassignp = new AstAssign( AstAssign* const bitassignp = new AstAssign{
nodep->fileline(), new AstVarRef(nodep->fileline(), bitvscp, VAccess::WRITE), nodep->fileline(), new AstVarRef{nodep->fileline(), bitvscp, VAccess::WRITE},
dimp); dimp};
nodep->addNextHere(bitassignp); nodep->addNextHere(bitassignp);
dimreadps.push_front(new AstVarRef(nodep->fileline(), bitvscp, VAccess::READ)); dimreadps.push_front(new AstVarRef{nodep->fileline(), bitvscp, VAccess::READ});
} }
} }
// //
@ -285,11 +285,11 @@ private:
+ cvtToStr(modVecNum)); + cvtToStr(modVecNum));
AstVarScope* const bitvscp AstVarScope* const bitvscp
= createVarSc(varrefp->varScopep(), bitvarname, lsbvaluep->width(), nullptr); = createVarSc(varrefp->varScopep(), bitvarname, lsbvaluep->width(), nullptr);
AstAssign* const bitassignp = new AstAssign( AstAssign* const bitassignp = new AstAssign{
nodep->fileline(), new AstVarRef(nodep->fileline(), bitvscp, VAccess::WRITE), nodep->fileline(), new AstVarRef{nodep->fileline(), bitvscp, VAccess::WRITE},
lsbvaluep); lsbvaluep};
nodep->addNextHere(bitassignp); nodep->addNextHere(bitassignp);
bitreadp = new AstVarRef(nodep->fileline(), bitvscp, VAccess::READ); bitreadp = new AstVarRef{nodep->fileline(), bitvscp, VAccess::READ};
} }
} }
// //
@ -303,8 +303,8 @@ private:
= (string("__Vdlyvval__") + oldvarp->shortName() + "__v" + cvtToStr(modVecNum)); = (string("__Vdlyvval__") + oldvarp->shortName() + "__v" + cvtToStr(modVecNum));
AstVarScope* const valvscp AstVarScope* const valvscp
= createVarSc(varrefp->varScopep(), valvarname, 0, nodep->rhsp()->dtypep()); = createVarSc(varrefp->varScopep(), valvarname, 0, nodep->rhsp()->dtypep());
newlhsp = new AstVarRef(nodep->fileline(), valvscp, VAccess::WRITE); newlhsp = new AstVarRef{nodep->fileline(), valvscp, VAccess::WRITE};
valreadp = new AstVarRef(nodep->fileline(), valvscp, VAccess::READ); valreadp = new AstVarRef{nodep->fileline(), valvscp, VAccess::READ};
} }
// //
//=== Setting/not setting boolean: __Vdlyvset__ //=== Setting/not setting boolean: __Vdlyvset__
@ -328,9 +328,9 @@ private:
nodep->fileline(), new AstVarRef{nodep->fileline(), setvscp, VAccess::WRITE}, nodep->fileline(), new AstVarRef{nodep->fileline(), setvscp, VAccess::WRITE},
new AstConst{nodep->fileline(), 0}}; new AstConst{nodep->fileline(), 0}};
} }
AstAssign* const setassignp = new AstAssign( AstAssign* const setassignp = new AstAssign{
nodep->fileline(), new AstVarRef(nodep->fileline(), setvscp, VAccess::WRITE), nodep->fileline(), new AstVarRef{nodep->fileline(), setvscp, VAccess::WRITE},
new AstConst(nodep->fileline(), AstConst::BitTrue())); new AstConst{nodep->fileline(), AstConst::BitTrue{}}};
nodep->addNextHere(setassignp); nodep->addNextHere(setassignp);
} }
if (m_nextDlyp) { // Tell next assigndly it can share the variable if (m_nextDlyp) { // Tell next assigndly it can share the variable
@ -344,11 +344,11 @@ private:
// It also has the nice side effect of assisting cache locality. // It also has the nice side effect of assisting cache locality.
AstNodeExpr* selectsp = varrefp; AstNodeExpr* selectsp = varrefp;
for (int dimension = int(dimreadps.size()) - 1; dimension >= 0; --dimension) { for (int dimension = int(dimreadps.size()) - 1; dimension >= 0; --dimension) {
selectsp = new AstArraySel(nodep->fileline(), selectsp, dimreadps[dimension]); selectsp = new AstArraySel{nodep->fileline(), selectsp, dimreadps[dimension]};
} }
if (bitselp) { if (bitselp) {
selectsp = new AstSel(nodep->fileline(), selectsp, bitreadp, selectsp = new AstSel{nodep->fileline(), selectsp, bitreadp,
bitselp->widthp()->cloneTree(false)); bitselp->widthp()->cloneTree(false)};
} }
// Build "IF (changeit) ... // Build "IF (changeit) ...
UINFO(9, " For " << setvscp << endl); UINFO(9, " For " << setvscp << endl);
@ -392,14 +392,14 @@ private:
UASSERT_OBJ(postLogicp, nodep, UASSERT_OBJ(postLogicp, nodep,
"Delayed assignment misoptimized; prev var found w/o associated IF"); "Delayed assignment misoptimized; prev var found w/o associated IF");
} else { } else {
postLogicp = new AstIf(nodep->fileline(), postLogicp = new AstIf{nodep->fileline(),
new AstVarRef(nodep->fileline(), setvscp, VAccess::READ)); new AstVarRef{nodep->fileline(), setvscp, VAccess::READ}};
UINFO(9, " Created " << postLogicp << endl); UINFO(9, " Created " << postLogicp << endl);
finalp->addStmtsp(postLogicp); finalp->addStmtsp(postLogicp);
finalp->user3p(setvscp); // Remember IF's vset variable finalp->user3p(setvscp); // Remember IF's vset variable
finalp->user4p(postLogicp); // and the associated IF, as we may be able to reuse it finalp->user4p(postLogicp); // and the associated IF, as we may be able to reuse it
} }
postLogicp->addThensp(new AstAssign(nodep->fileline(), selectsp, valreadp)); postLogicp->addThensp(new AstAssign{nodep->fileline(), selectsp, valreadp});
if (m_procp->isSuspendable()) { if (m_procp->isSuspendable()) {
FileLine* const flp = nodep->fileline(); FileLine* const flp = nodep->fileline();
postLogicp->addThensp(new AstAssign{flp, new AstVarRef{flp, setvscp, VAccess::WRITE}, postLogicp->addThensp(new AstAssign{flp, new AstVarRef{flp, setvscp, VAccess::WRITE},
@ -579,7 +579,7 @@ private:
newactp->addStmtsp(postp); newactp->addStmtsp(postp);
} }
AstVarRef* const newrefp AstVarRef* const newrefp
= new AstVarRef(nodep->fileline(), dlyvscp, VAccess::WRITE); = new AstVarRef{nodep->fileline(), dlyvscp, VAccess::WRITE};
newrefp->user2(true); // No reason to do it again newrefp->user2(true); // No reason to do it again
nodep->replaceWith(newrefp); nodep->replaceWith(newrefp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);

View File

@ -349,7 +349,7 @@ private:
if (m_scopep) { if (m_scopep) {
UINFO(5, " STMT " << nodep << endl); UINFO(5, " STMT " << nodep << endl);
// m_activep is null under AstCFunc's, that's ok. // m_activep is null under AstCFunc's, that's ok.
m_logicVertexp = new GateLogicVertex(&m_graph, m_scopep, nodep, m_activep, m_inSlow); m_logicVertexp = new GateLogicVertex{&m_graph, m_scopep, nodep, m_activep, m_inSlow};
if (nonReducibleReason) { if (nonReducibleReason) {
m_logicVertexp->clearReducibleAndDedupable(nonReducibleReason); m_logicVertexp->clearReducibleAndDedupable(nonReducibleReason);
} else if (!m_activeReducible) { } else if (!m_activeReducible) {
@ -368,7 +368,7 @@ private:
GateVarVertex* vertexp = reinterpret_cast<GateVarVertex*>(varscp->user1p()); GateVarVertex* vertexp = reinterpret_cast<GateVarVertex*>(varscp->user1p());
if (!vertexp) { if (!vertexp) {
UINFO(6, "New vertex " << varscp << endl); UINFO(6, "New vertex " << varscp << endl);
vertexp = new GateVarVertex(&m_graph, m_scopep, varscp); vertexp = new GateVarVertex{&m_graph, m_scopep, varscp};
varscp->user1p(vertexp); varscp->user1p(vertexp);
if (varscp->varp()->isSigPublic()) { if (varscp->varp()->isSigPublic()) {
// Public signals shouldn't be changed, pli code might be messing with them // Public signals shouldn't be changed, pli code might be messing with them
@ -493,10 +493,10 @@ private:
// We use weight of one; if we ref the var more than once, when we simplify, // We use weight of one; if we ref the var more than once, when we simplify,
// the weight will increase // the weight will increase
if (nodep->access().isWriteOrRW()) { if (nodep->access().isWriteOrRW()) {
new V3GraphEdge(&m_graph, m_logicVertexp, vvertexp, 1); new V3GraphEdge{&m_graph, m_logicVertexp, vvertexp, 1};
} }
if (nodep->access().isReadOrRW()) { if (nodep->access().isReadOrRW()) {
new V3GraphEdge(&m_graph, vvertexp, m_logicVertexp, 1); new V3GraphEdge{&m_graph, vvertexp, m_logicVertexp, 1};
} }
} }
} }
@ -638,7 +638,7 @@ void GateVisitor::optimizeSignals(bool allowMultiIn) {
for (AstNodeVarRef* const refp : rhsVarRefs) { for (AstNodeVarRef* const refp : rhsVarRefs) {
AstVarScope* const newvarscp = refp->varScopep(); AstVarScope* const newvarscp = refp->varScopep();
GateVarVertex* const varvertexp = makeVarVertex(newvarscp); GateVarVertex* const varvertexp = makeVarVertex(newvarscp);
new V3GraphEdge(&m_graph, varvertexp, consumeVertexp, 1); new V3GraphEdge{&m_graph, varvertexp, consumeVertexp, 1};
// Propagate clock attribute onto generating node // Propagate clock attribute onto generating node
varvertexp->propagateAttrClocksFrom(vvertexp); varvertexp->propagateAttrClocksFrom(vvertexp);
} }
@ -1177,8 +1177,8 @@ private:
const AstConst* const cwidth = VN_CAST(cur->widthp(), Const); const AstConst* const cwidth = VN_CAST(cur->widthp(), Const);
if (!pstart || !pwidth || !cstart || !cwidth) return nullptr; // too complicated if (!pstart || !pwidth || !cstart || !cwidth) return nullptr; // too complicated
if (cur->lsbConst() + cur->widthConst() == pre->lsbConst()) { if (cur->lsbConst() + cur->widthConst() == pre->lsbConst()) {
return new AstSel(curVarRefp->fileline(), curVarRefp->cloneTree(false), return new AstSel{curVarRefp->fileline(), curVarRefp->cloneTree(false),
cur->lsbConst(), pre->widthConst() + cur->widthConst()); cur->lsbConst(), pre->widthConst() + cur->widthConst()};
} else { } else {
return nullptr; return nullptr;
} }
@ -1218,9 +1218,9 @@ private:
preselp->replaceWith(newselp); preselp->replaceWith(newselp);
VL_DO_DANGLING(preselp->deleteTree(), preselp); VL_DO_DANGLING(preselp->deleteTree(), preselp);
// create new rhs for pre assignment // create new rhs for pre assignment
AstNode* const newrhsp = new AstConcat( AstNode* const newrhsp = new AstConcat{
m_assignp->rhsp()->fileline(), m_assignp->rhsp()->cloneTree(false), m_assignp->rhsp()->fileline(), m_assignp->rhsp()->cloneTree(false),
assignp->rhsp()->cloneTree(false)); assignp->rhsp()->cloneTree(false)};
AstNode* const oldrhsp = m_assignp->rhsp(); AstNode* const oldrhsp = m_assignp->rhsp();
oldrhsp->replaceWith(newrhsp); oldrhsp->replaceWith(newrhsp);
VL_DO_DANGLING(oldrhsp->deleteTree(), oldrhsp); VL_DO_DANGLING(oldrhsp->deleteTree(), oldrhsp);
@ -1240,7 +1240,7 @@ private:
ledgep = ledgep->inNextp(); ledgep = ledgep->inNextp();
GateEitherVertex* const fromvp GateEitherVertex* const fromvp
= static_cast<GateEitherVertex*>(oedgep->fromp()); = static_cast<GateEitherVertex*>(oedgep->fromp());
new V3GraphEdge(m_graphp, fromvp, m_logicvp, 1); new V3GraphEdge{m_graphp, fromvp, m_logicvp, 1};
VL_DO_DANGLING(oedgep->unlinkDelete(), oedgep); VL_DO_DANGLING(oedgep->unlinkDelete(), oedgep);
} }
} }
@ -1369,7 +1369,7 @@ private:
m_total_seen_clk_vectors++; m_total_seen_clk_vectors++;
} }
const GateClkDecompState* const currState = reinterpret_cast<GateClkDecompState*>(vu.c()); const GateClkDecompState* const currState = reinterpret_cast<GateClkDecompState*>(vu.c());
GateClkDecompState nextState(currState->m_offset, vsp); GateClkDecompState nextState{currState->m_offset, vsp};
vvertexp->iterateCurrentOutEdges(*this, VNUser{&nextState}); vvertexp->iterateCurrentOutEdges(*this, VNUser{&nextState});
if (vsp->varp()->width() > 1) --m_seen_clk_vectors; if (vsp->varp()->width() > 1) --m_seen_clk_vectors;
vsp->user2(false); vsp->user2(false);
@ -1424,17 +1424,17 @@ private:
UINFO(9, "CLK DECOMP Connecting - " << assignp->lhsp() << endl); UINFO(9, "CLK DECOMP Connecting - " << assignp->lhsp() << endl);
UINFO(9, " to - " << m_clk_vsp << endl); UINFO(9, " to - " << m_clk_vsp << endl);
AstNode* const rhsp = assignp->rhsp(); AstNode* const rhsp = assignp->rhsp();
rhsp->replaceWith(new AstVarRef(rhsp->fileline(), m_clk_vsp, VAccess::READ)); rhsp->replaceWith(new AstVarRef{rhsp->fileline(), m_clk_vsp, VAccess::READ});
while (V3GraphEdge* const edgep = lvertexp->inBeginp()) { while (V3GraphEdge* const edgep = lvertexp->inBeginp()) {
VL_DO_DANGLING(edgep->unlinkDelete(), edgep); VL_DO_DANGLING(edgep->unlinkDelete(), edgep);
} }
new V3GraphEdge(m_graphp, m_clk_vvertexp, lvertexp, 1); new V3GraphEdge{m_graphp, m_clk_vvertexp, lvertexp, 1};
m_total_decomposed_clk_vectors++; m_total_decomposed_clk_vectors++;
} }
} else { } else {
return VNUser{0}; return VNUser{0};
} }
GateClkDecompState nextState(clk_offset, currState->m_last_vsp); GateClkDecompState nextState{clk_offset, currState->m_last_vsp};
return lvertexp->iterateCurrentOutEdges(*this, VNUser{&nextState}); return lvertexp->iterateCurrentOutEdges(*this, VNUser{&nextState});
} }
return VNUser{0}; return VNUser{0};
@ -1453,7 +1453,7 @@ public:
m_seen_clk_vectors = 0; m_seen_clk_vectors = 0;
m_clk_vsp = vvertexp->varScp(); m_clk_vsp = vvertexp->varScp();
m_clk_vvertexp = vvertexp; m_clk_vvertexp = vvertexp;
GateClkDecompState nextState(0, m_clk_vsp); GateClkDecompState nextState{0, m_clk_vsp};
vvertexp->accept(*this, VNUser{&nextState}); vvertexp->accept(*this, VNUser{&nextState});
} }
}; };

View File

@ -76,18 +76,18 @@ private:
if (nodep->modVarp()->isInoutish()) { if (nodep->modVarp()->isInoutish()) {
nodep->v3fatalSrc("Unsupported: Verilator is a 2-state simulator"); nodep->v3fatalSrc("Unsupported: Verilator is a 2-state simulator");
} else if (nodep->modVarp()->isWritable()) { } else if (nodep->modVarp()->isWritable()) {
AstNodeExpr* const rhsp = new AstVarXRef(exprp->fileline(), nodep->modVarp(), AstNodeExpr* const rhsp = new AstVarXRef{exprp->fileline(), nodep->modVarp(),
m_cellp->name(), VAccess::READ); m_cellp->name(), VAccess::READ};
AstAssignW* const assp = new AstAssignW(exprp->fileline(), exprp, rhsp); AstAssignW* const assp = new AstAssignW{exprp->fileline(), exprp, rhsp};
m_cellp->addNextHere(assp); m_cellp->addNextHere(assp);
} else if (nodep->modVarp()->isNonOutput()) { } else if (nodep->modVarp()->isNonOutput()) {
// Don't bother moving constants now, // Don't bother moving constants now,
// we'll be pushing the const down to the cell soon enough. // we'll be pushing the const down to the cell soon enough.
AstNode* const assp AstNode* const assp
= new AstAssignW(exprp->fileline(), = new AstAssignW{exprp->fileline(),
new AstVarXRef(exprp->fileline(), nodep->modVarp(), new AstVarXRef{exprp->fileline(), nodep->modVarp(),
m_cellp->name(), VAccess::WRITE), m_cellp->name(), VAccess::WRITE},
exprp); exprp};
m_cellp->addNextHere(assp); m_cellp->addNextHere(assp);
if (debug() >= 9) assp->dumpTree(cout, " _new: "); if (debug() >= 9) assp->dumpTree(cout, " _new: ");
} else if (nodep->modVarp()->isIfaceRef() } else if (nodep->modVarp()->isIfaceRef()
@ -97,14 +97,14 @@ private:
IfaceRefDType))) { IfaceRefDType))) {
// Create an AstAssignVarScope for Vars to Cells so we can // Create an AstAssignVarScope for Vars to Cells so we can
// link with their scope later // link with their scope later
AstNodeExpr* const lhsp = new AstVarXRef(exprp->fileline(), nodep->modVarp(), AstNodeExpr* const lhsp = new AstVarXRef{exprp->fileline(), nodep->modVarp(),
m_cellp->name(), VAccess::READ); m_cellp->name(), VAccess::READ};
const AstVarRef* const refp = VN_CAST(exprp, VarRef); const AstVarRef* const refp = VN_CAST(exprp, VarRef);
const AstVarXRef* const xrefp = VN_CAST(exprp, VarXRef); const AstVarXRef* const xrefp = VN_CAST(exprp, VarXRef);
UASSERT_OBJ(refp || xrefp, exprp, UASSERT_OBJ(refp || xrefp, exprp,
"Interfaces: Pin is not connected to a VarRef or VarXRef"); "Interfaces: Pin is not connected to a VarRef or VarXRef");
AstAssignVarScope* const assp AstAssignVarScope* const assp
= new AstAssignVarScope(exprp->fileline(), lhsp, exprp); = new AstAssignVarScope{exprp->fileline(), lhsp, exprp};
m_cellp->addNextHere(assp); m_cellp->addNextHere(assp);
} else { } else {
nodep->v3error("Assigned pin is neither input nor output"); nodep->v3error("Assigned pin is neither input nor output");
@ -335,7 +335,7 @@ private:
? (rangep->elementsConst() - 1 - m_instSelNum) ? (rangep->elementsConst() - 1 - m_instSelNum)
: m_instSelNum; : m_instSelNum;
AstNodeExpr* exprp = VN_AS(nodep->exprp(), NodeExpr)->unlinkFrBack(); AstNodeExpr* exprp = VN_AS(nodep->exprp(), NodeExpr)->unlinkFrBack();
exprp = new AstArraySel(exprp->fileline(), exprp, arraySelNum); exprp = new AstArraySel{exprp->fileline(), exprp, arraySelNum};
nodep->exprp(exprp); nodep->exprp(exprp);
} else if (expwidth == modwidth) { } else if (expwidth == modwidth) {
// NOP: Arrayed instants: widths match so connect to each instance // NOP: Arrayed instants: widths match so connect to each instance
@ -358,7 +358,7 @@ private:
"with output connections to non-wires."); "with output connections to non-wires.");
// Note spec allows more complicated matches such as slices and such // Note spec allows more complicated matches such as slices and such
} }
exprp = new AstSel(exprp->fileline(), exprp, modwidth * m_instSelNum, modwidth); exprp = new AstSel{exprp->fileline(), exprp, modwidth * m_instSelNum, modwidth};
nodep->exprp(exprp); nodep->exprp(exprp);
} else { } else {
nodep->v3fatalSrc("Width mismatch; V3Width should have errored out."); nodep->v3fatalSrc("Width mismatch; V3Width should have errored out.");
@ -382,9 +382,9 @@ private:
arrselp->lhsp()->v3error("Unsupported: interface slices"); arrselp->lhsp()->v3error("Unsupported: interface slices");
const AstVarRef* const varrefp = VN_CAST(arrselp->lhsp(), VarRef); const AstVarRef* const varrefp = VN_CAST(arrselp->lhsp(), VarRef);
UASSERT_OBJ(varrefp, arrselp, "No interface varref under array"); UASSERT_OBJ(varrefp, arrselp, "No interface varref under array");
AstVarXRef* const newp = new AstVarXRef( AstVarXRef* const newp = new AstVarXRef{
nodep->fileline(), varrefp->name() + "__BRA__" + index + "__KET__", "", nodep->fileline(), varrefp->name() + "__BRA__" + index + "__KET__", "",
VAccess::WRITE); VAccess::WRITE};
newp->dtypep(nodep->modVarp()->dtypep()); newp->dtypep(nodep->modVarp()->dtypep());
newp->classOrPackagep(varrefp->classOrPackagep()); newp->classOrPackagep(varrefp->classOrPackagep());
arrselp->addNextHere(newp); arrselp->addNextHere(newp);
@ -453,7 +453,7 @@ private:
const string newname = varrefp->name() + "__BRA__" + cvtToStr(expr_i) + "__KET__"; const string newname = varrefp->name() + "__BRA__" + cvtToStr(expr_i) + "__KET__";
AstVarXRef* const newVarXRefp AstVarXRef* const newVarXRefp
= new AstVarXRef(nodep->fileline(), newname, "", VAccess::WRITE); = new AstVarXRef{nodep->fileline(), newname, "", VAccess::WRITE};
newVarXRefp->varp(newp->modVarp()); newVarXRefp->varp(newp->modVarp());
newp->exprp()->unlinkFrBack()->deleteTree(); newp->exprp()->unlinkFrBack()->deleteTree();
newp->exprp(newVarXRefp); newp->exprp(newVarXRefp);
@ -517,10 +517,10 @@ public:
// otherwise done // otherwise done
if (pinVarp->direction() == VDirection::INPUT if (pinVarp->direction() == VDirection::INPUT
&& cellp->modp()->unconnectedDrive().isSetTrue()) { && cellp->modp()->unconnectedDrive().isSetTrue()) {
pinp->exprp(new AstConst(pinp->fileline(), AstConst::StringToParse(), "'1")); pinp->exprp(new AstConst{pinp->fileline(), AstConst::StringToParse{}, "'1"});
} else if (pinVarp->direction() == VDirection::INPUT } else if (pinVarp->direction() == VDirection::INPUT
&& cellp->modp()->unconnectedDrive().isSetFalse()) { && cellp->modp()->unconnectedDrive().isSetFalse()) {
pinp->exprp(new AstConst(pinp->fileline(), AstConst::StringToParse(), "'0")); pinp->exprp(new AstConst{pinp->fileline(), AstConst::StringToParse{}, "'0"});
} else { } else {
return nullptr; return nullptr;
} }
@ -559,7 +559,7 @@ public:
// Prevent name conflict if both tri & non-tri add signals // Prevent name conflict if both tri & non-tri add signals
+ (forTristate ? "t" : "") + "__" + cellp->name() + "__" + pinp->name()); + (forTristate ? "t" : "") + "__" + cellp->name() + "__" + pinp->name());
AstVar* const newvarp AstVar* const newvarp
= new AstVar(pinVarp->fileline(), VVarType::MODULETEMP, newvarname, pinVarp); = new AstVar{pinVarp->fileline(), VVarType::MODULETEMP, newvarname, pinVarp};
// Important to add statement next to cell, in case there is a // Important to add statement next to cell, in case there is a
// generate with same named cell // generate with same named cell
cellp->addNextHere(newvarp); cellp->addNextHere(newvarp);
@ -568,19 +568,19 @@ public:
" direct one-to-one connection (without any expression)"); " direct one-to-one connection (without any expression)");
} else if (pinVarp->isWritable()) { } else if (pinVarp->isWritable()) {
// See also V3Inst // See also V3Inst
AstNodeExpr* rhsp = new AstVarRef(pinp->fileline(), newvarp, VAccess::READ); AstNodeExpr* rhsp = new AstVarRef{pinp->fileline(), newvarp, VAccess::READ};
UINFO(5, "pinRecon width " << pinVarp->width() << " >? " << rhsp->width() << " >? " UINFO(5, "pinRecon width " << pinVarp->width() << " >? " << rhsp->width() << " >? "
<< pinexprp->width() << endl); << pinexprp->width() << endl);
rhsp = extendOrSel(pinp->fileline(), rhsp, pinVarp); rhsp = extendOrSel(pinp->fileline(), rhsp, pinVarp);
pinp->exprp(new AstVarRef(newvarp->fileline(), newvarp, VAccess::WRITE)); pinp->exprp(new AstVarRef{newvarp->fileline(), newvarp, VAccess::WRITE});
AstNodeExpr* const rhsSelp = extendOrSel(pinp->fileline(), rhsp, pinexprp); AstNodeExpr* const rhsSelp = extendOrSel(pinp->fileline(), rhsp, pinexprp);
assignp = new AstAssignW(pinp->fileline(), pinexprp, rhsSelp); assignp = new AstAssignW{pinp->fileline(), pinexprp, rhsSelp};
} else { } else {
// V3 width should have range/extended to make the widths correct // V3 width should have range/extended to make the widths correct
assignp = new AstAssignW(pinp->fileline(), assignp = new AstAssignW{pinp->fileline(),
new AstVarRef(pinp->fileline(), newvarp, VAccess::WRITE), new AstVarRef{pinp->fileline(), newvarp, VAccess::WRITE},
pinexprp); pinexprp};
pinp->exprp(new AstVarRef(pinexprp->fileline(), newvarp, VAccess::READ)); pinp->exprp(new AstVarRef{pinexprp->fileline(), newvarp, VAccess::READ});
} }
if (assignp) cellp->addNextHere(assignp); if (assignp) cellp->addNextHere(assignp);
// if (debug()) pinp->dumpTree(cout, "- out:"); // if (debug()) pinp->dumpTree(cout, "- out:");

View File

@ -289,7 +289,7 @@ public:
} }
void insertDUnit(AstNetlist* nodep) { void insertDUnit(AstNetlist* nodep) {
// $unit on top scope // $unit on top scope
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, " INSERTdunit se" << cvtToHex(symp) << endl); UINFO(9, " INSERTdunit se" << cvtToHex(symp) << endl);
symp->parentp(rootEntp()); // Needed so backward search can find name of top module symp->parentp(rootEntp()); // Needed so backward search can find name of top module
symp->fallbackp(nullptr); symp->fallbackp(nullptr);
@ -300,7 +300,7 @@ public:
} }
VSymEnt* insertTopCell(AstNodeModule* nodep, const string& scopename) { VSymEnt* insertTopCell(AstNodeModule* nodep, const string& scopename) {
// Only called on the module at the very top of the hierarchy // Only called on the module at the very top of the hierarchy
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, UINFO(9,
" INSERTtop se" << cvtToHex(symp) << " " << scopename << " " << nodep << endl); " INSERTtop se" << cvtToHex(symp) << " " << scopename << " " << nodep << endl);
symp->parentp(rootEntp()); // Needed so backward search can find name of top module symp->parentp(rootEntp()); // Needed so backward search can find name of top module
@ -327,7 +327,7 @@ public:
VSymEnt* insertCell(VSymEnt* abovep, VSymEnt* modSymp, AstCell* nodep, VSymEnt* insertCell(VSymEnt* abovep, VSymEnt* modSymp, AstCell* nodep,
const string& scopename) { const string& scopename) {
UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node"); UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node");
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, " INSERTcel se" << cvtToHex(symp) << " " << scopename << " above=se" UINFO(9, " INSERTcel se" << cvtToHex(symp) << " " << scopename << " above=se"
<< cvtToHex(abovep) << " mods=se" << cvtToHex(modSymp) << cvtToHex(abovep) << " mods=se" << cvtToHex(modSymp)
<< " node=" << nodep << endl); << " node=" << nodep << endl);
@ -355,7 +355,7 @@ public:
// A fake point in the hierarchy, corresponding to an inlined module // A fake point in the hierarchy, corresponding to an inlined module
// This references to another Sym, and eventually resolves to a module with a prefix // This references to another Sym, and eventually resolves to a module with a prefix
UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node"); UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node");
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, " INSERTinl se" << cvtToHex(symp) << " " << basename << " above=se" UINFO(9, " INSERTinl se" << cvtToHex(symp) << " " << basename << " above=se"
<< cvtToHex(abovep) << " mods=se" << cvtToHex(modSymp) << cvtToHex(abovep) << " mods=se" << cvtToHex(modSymp)
<< " node=" << nodep << endl); << " node=" << nodep << endl);
@ -378,7 +378,7 @@ public:
// Note we fallback to the symbol table of the parent, as we want to find variables there // Note we fallback to the symbol table of the parent, as we want to find variables there
// However, cells walk the graph, so cells will appear under the begin/ftask itself // However, cells walk the graph, so cells will appear under the begin/ftask itself
UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node"); UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node");
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, " INSERTblk se" << cvtToHex(symp) << " above=se" << cvtToHex(abovep) UINFO(9, " INSERTblk se" << cvtToHex(symp) << " above=se" << cvtToHex(abovep)
<< " pkg=" << cvtToHex(classOrPackagep) << " node=" << nodep << " pkg=" << cvtToHex(classOrPackagep) << " node=" << nodep
<< endl); << endl);
@ -394,7 +394,7 @@ public:
VSymEnt* insertSym(VSymEnt* abovep, const string& name, AstNode* nodep, VSymEnt* insertSym(VSymEnt* abovep, const string& name, AstNode* nodep,
AstNodeModule* classOrPackagep) { AstNodeModule* classOrPackagep) {
UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node"); UASSERT_OBJ(abovep, nodep, "Null symbol table inserting node");
VSymEnt* const symp = new VSymEnt(&m_syms, nodep); VSymEnt* const symp = new VSymEnt{&m_syms, nodep};
UINFO(9, " INSERTsym se" << cvtToHex(symp) << " name='" << name << "' above=se" UINFO(9, " INSERTsym se" << cvtToHex(symp) << " name='" << name << "' above=se"
<< cvtToHex(abovep) << " pkg=" << cvtToHex(classOrPackagep) << cvtToHex(abovep) << " pkg=" << cvtToHex(classOrPackagep)
<< " node=" << nodep << endl); << " node=" << nodep << endl);
@ -503,7 +503,7 @@ public:
} }
if (!ok) { if (!ok) {
const string suggest = suggestSymFallback(ifaceSymp, ifacerefp->modportName(), const string suggest = suggestSymFallback(ifaceSymp, ifacerefp->modportName(),
LinkNodeMatcherModport()); LinkNodeMatcherModport{});
ifacerefp->modportFileline()->v3error( ifacerefp->modportFileline()->v3error(
"Modport not found under interface " "Modport not found under interface "
<< ifacerefp->prettyNameQ(ifacerefp->ifaceName()) << ": " << ifacerefp->prettyNameQ(ifacerefp->ifaceName()) << ": "
@ -753,7 +753,7 @@ class LinkDotFindVisitor final : public VNVisitor {
// METHODS // METHODS
void makeImplicitNew(AstClass* nodep) { void makeImplicitNew(AstClass* nodep) {
AstFunc* const newp = new AstFunc(nodep->fileline(), "new", nullptr, nullptr); AstFunc* const newp = new AstFunc{nodep->fileline(), "new", nullptr, nullptr};
newp->isConstructor(true); newp->isConstructor(true);
nodep->addMembersp(newp); nodep->addMembersp(newp);
UINFO(8, "Made implicit new for " << nodep->name() << ": " << nodep << endl); UINFO(8, "Made implicit new for " << nodep->name() << ": " << nodep << endl);
@ -1103,11 +1103,11 @@ class LinkDotFindVisitor final : public VNVisitor {
if (dtypep) { if (dtypep) {
dtypep->unlinkFrBack(); dtypep->unlinkFrBack();
} else { } else {
dtypep = new AstBasicDType(nodep->fileline(), VBasicDTypeKwd::LOGIC); dtypep = new AstBasicDType{nodep->fileline(), VBasicDTypeKwd::LOGIC};
} }
AstVar* const newvarp AstVar* const newvarp
= new AstVar(nodep->fileline(), VVarType::VAR, nodep->name(), = new AstVar{nodep->fileline(), VVarType::VAR, nodep->name(),
VFlagChildDType{}, dtypep); // Not dtype resolved yet VFlagChildDType{}, dtypep}; // Not dtype resolved yet
newvarp->direction(VDirection::OUTPUT); newvarp->direction(VDirection::OUTPUT);
newvarp->lifetime(VLifetime::AUTOMATIC); newvarp->lifetime(VLifetime::AUTOMATIC);
newvarp->funcReturn(true); newvarp->funcReturn(true);
@ -1180,7 +1180,7 @@ class LinkDotFindVisitor final : public VNVisitor {
findvarp->fileline()->modifyStateInherit(nodep->fileline()); findvarp->fileline()->modifyStateInherit(nodep->fileline());
if (nodep->getChildDTypep()->numeric().isSigned() if (nodep->getChildDTypep()->numeric().isSigned()
&& !findvarp->getChildDTypep()->numeric().isSigned()) { && !findvarp->getChildDTypep()->numeric().isSigned()) {
findvarp->getChildDTypep()->numeric(VSigning(true)); findvarp->getChildDTypep()->numeric(VSigning{true});
} }
AstBasicDType* const bdtypep AstBasicDType* const bdtypep
= VN_CAST(findvarp->childDTypep(), BasicDType); = VN_CAST(findvarp->childDTypep(), BasicDType);
@ -1424,10 +1424,10 @@ class LinkDotFindVisitor final : public VNVisitor {
} }
// Type depends on the method used, let V3Width figure it out later // Type depends on the method used, let V3Width figure it out later
if (nodep->exprp()) { // Else empty expression and pretend no "with" if (nodep->exprp()) { // Else empty expression and pretend no "with"
const auto indexArgRefp = new AstLambdaArgRef(argFl, name + "__DOT__index", true); const auto indexArgRefp = new AstLambdaArgRef{argFl, name + "__DOT__index", true};
const auto valueArgRefp = new AstLambdaArgRef(argFl, name, false); const auto valueArgRefp = new AstLambdaArgRef{argFl, name, false};
const auto newp = new AstWith(nodep->fileline(), indexArgRefp, valueArgRefp, const auto newp = new AstWith{nodep->fileline(), indexArgRefp, valueArgRefp,
nodep->exprp()->unlinkFrBackWithNext()); nodep->exprp()->unlinkFrBackWithNext()};
funcrefp->addPinsp(newp); funcrefp->addPinsp(newp);
} }
nodep->replaceWith(funcrefp->unlinkFrBack()); nodep->replaceWith(funcrefp->unlinkFrBack());
@ -1544,9 +1544,9 @@ private:
UINFO(9, "Defparam cell " << nodep->path() << "." << nodep->name() << " attach-to " UINFO(9, "Defparam cell " << nodep->path() << "." << nodep->name() << " attach-to "
<< cellp << " <= " << exprp << endl); << cellp << " <= " << exprp << endl);
// Don't need to check the name of the defparam exists. V3Param does. // Don't need to check the name of the defparam exists. V3Param does.
AstPin* const pinp = new AstPin(nodep->fileline(), AstPin* const pinp = new AstPin{nodep->fileline(),
-1, // Pin# not relevant -1, // Pin# not relevant
nodep->name(), exprp); nodep->name(), exprp};
cellp->addParamsp(pinp); cellp->addParamsp(pinp);
} }
VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep);
@ -1985,7 +1985,7 @@ private:
if (!noWarn) { if (!noWarn) {
if (nodep->fileline()->warnIsOff(V3ErrorCode::I_DEF_NETTYPE_WIRE)) { if (nodep->fileline()->warnIsOff(V3ErrorCode::I_DEF_NETTYPE_WIRE)) {
const string suggest = m_statep->suggestSymFallback(moduleSymp, nodep->name(), const string suggest = m_statep->suggestSymFallback(moduleSymp, nodep->name(),
LinkNodeMatcherVar()); LinkNodeMatcherVar{});
nodep->v3error("Signal definition not found, and implicit disabled with " nodep->v3error("Signal definition not found, and implicit disabled with "
"`default_nettype: " "`default_nettype: "
<< nodep->prettyNameQ() << '\n' << nodep->prettyNameQ() << '\n'
@ -1996,15 +1996,15 @@ private:
// as there could be thousands of these suppressed in large netlists // as there could be thousands of these suppressed in large netlists
else if (!nodep->fileline()->warnIsOff(V3ErrorCode::IMPLICIT)) { else if (!nodep->fileline()->warnIsOff(V3ErrorCode::IMPLICIT)) {
const string suggest = m_statep->suggestSymFallback(moduleSymp, nodep->name(), const string suggest = m_statep->suggestSymFallback(moduleSymp, nodep->name(),
LinkNodeMatcherVar()); LinkNodeMatcherVar{});
nodep->v3warn(IMPLICIT, nodep->v3warn(IMPLICIT,
"Signal definition not found, creating implicitly: " "Signal definition not found, creating implicitly: "
<< nodep->prettyNameQ() << '\n' << nodep->prettyNameQ() << '\n'
<< (suggest.empty() ? "" : nodep->warnMore() + suggest)); << (suggest.empty() ? "" : nodep->warnMore() + suggest));
} }
} }
AstVar* const newp = new AstVar(nodep->fileline(), VVarType::WIRE, nodep->name(), AstVar* const newp = new AstVar{nodep->fileline(), VVarType::WIRE, nodep->name(),
VFlagLogicPacked{}, 1); VFlagLogicPacked{}, 1};
newp->trace(modp->modTrace()); newp->trace(modp->modTrace());
nodep->varp(newp); nodep->varp(newp);
modp->addStmtsp(newp); modp->addStmtsp(newp);
@ -2184,9 +2184,9 @@ private:
} }
const string suggest const string suggest
= (nodep->param() ? m_statep->suggestSymFlat(m_pinSymp, nodep->name(), = (nodep->param() ? m_statep->suggestSymFlat(m_pinSymp, nodep->name(),
LinkNodeMatcherVarParam()) LinkNodeMatcherVarParam{})
: m_statep->suggestSymFlat(m_pinSymp, nodep->name(), : m_statep->suggestSymFlat(m_pinSymp, nodep->name(),
LinkNodeMatcherVarIO())); LinkNodeMatcherVarIO{}));
nodep->v3warn(PINNOTFOUND, nodep->v3warn(PINNOTFOUND,
ucfirst(whatp) ucfirst(whatp)
<< " not found: " << nodep->prettyNameQ() << '\n' << " not found: " << nodep->prettyNameQ() << '\n'
@ -2286,7 +2286,7 @@ private:
if (start) { if (start) {
AstNode* newp; AstNode* newp;
if (m_ds.m_dotErr) { if (m_ds.m_dotErr) {
newp = new AstConst(nodep->fileline(), AstConst::BitFalse()); newp = new AstConst{nodep->fileline(), AstConst::BitFalse{}};
} else { } else {
// RHS is what we're left with // RHS is what we're left with
newp = nodep->rhsp()->unlinkFrBack(); newp = nodep->rhsp()->unlinkFrBack();
@ -2297,8 +2297,8 @@ private:
} else { // Dot midpoint } else { // Dot midpoint
AstNodeExpr* newp = nodep->rhsp()->unlinkFrBack(); AstNodeExpr* newp = nodep->rhsp()->unlinkFrBack();
if (m_ds.m_unresolved) { if (m_ds.m_unresolved) {
AstCellRef* const crp = new AstCellRef(nodep->fileline(), nodep->name(), AstCellRef* const crp = new AstCellRef{nodep->fileline(), nodep->name(),
nodep->lhsp()->unlinkFrBack(), newp); nodep->lhsp()->unlinkFrBack(), newp};
newp = crp; newp = crp;
} }
nodep->replaceWith(newp); nodep->replaceWith(newp);
@ -2351,8 +2351,8 @@ private:
&& nodep->name() == "index") { && nodep->name() == "index") {
// 'with' statement's 'item.index' // 'with' statement's 'item.index'
iterateChildren(nodep); iterateChildren(nodep);
const auto newp = new AstLambdaArgRef( const auto newp = new AstLambdaArgRef{
nodep->fileline(), m_ds.m_unlinkedScopep->name() + "__DOT__index", true); nodep->fileline(), m_ds.m_unlinkedScopep->name() + "__DOT__index", true};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
return; return;
@ -2360,7 +2360,7 @@ private:
// Found a Var, everything following is membership. {scope}.{var}.HERE {member} // Found a Var, everything following is membership. {scope}.{var}.HERE {member}
AstNodeExpr* const varEtcp = m_ds.m_dotp->lhsp()->unlinkFrBack(); AstNodeExpr* const varEtcp = m_ds.m_dotp->lhsp()->unlinkFrBack();
AstNodeExpr* const newp AstNodeExpr* const newp
= new AstMemberSel(nodep->fileline(), varEtcp, VFlagChildDType(), nodep->name()); = new AstMemberSel{nodep->fileline(), varEtcp, VFlagChildDType{}, nodep->name()};
if (m_ds.m_dotErr) { if (m_ds.m_dotErr) {
nodep->unlinkFrBack(); // Avoid circular node loop on errors nodep->unlinkFrBack(); // Avoid circular node loop on errors
} else { } else {
@ -2462,15 +2462,15 @@ private:
m_ds.m_dotSymp = m_statep->getNodeSym(ifacerefp->ifaceViaCellp()); m_ds.m_dotSymp = m_statep->getNodeSym(ifacerefp->ifaceViaCellp());
m_ds.m_dotPos = DP_SCOPE; m_ds.m_dotPos = DP_SCOPE;
ok = true; ok = true;
AstNode* const newp = new AstVarRef(nodep->fileline(), varp, VAccess::READ); AstNode* const newp = new AstVarRef{nodep->fileline(), varp, VAccess::READ};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
} else if (allowVar) { } else if (allowVar) {
AstNode* newp; AstNode* newp;
if (m_ds.m_dotText != "") { if (m_ds.m_dotText != "") {
AstVarXRef* const refp AstVarXRef* const refp
= new AstVarXRef(nodep->fileline(), nodep->name(), m_ds.m_dotText, = new AstVarXRef{nodep->fileline(), nodep->name(), m_ds.m_dotText,
VAccess::READ); // lvalue'ness computed later VAccess::READ}; // lvalue'ness computed later
refp->varp(varp); refp->varp(varp);
if (varp->attrSplitVar()) { if (varp->attrSplitVar()) {
refp->v3warn( refp->v3warn(
@ -2490,8 +2490,8 @@ private:
refp->dotted(dotted.substr(0, pos)); refp->dotted(dotted.substr(0, pos));
newp = refp; newp = refp;
} else { } else {
newp = new AstUnlinkedRef(nodep->fileline(), refp, refp->name(), newp = new AstUnlinkedRef{nodep->fileline(), refp, refp->name(),
m_ds.m_unlinkedScopep->unlinkFrBack()); m_ds.m_unlinkedScopep->unlinkFrBack()};
m_ds.m_unlinkedScopep = nullptr; m_ds.m_unlinkedScopep = nullptr;
m_ds.m_unresolved = false; m_ds.m_unresolved = false;
} }
@ -2499,9 +2499,8 @@ private:
newp = refp; newp = refp;
} }
} else { } else {
AstVarRef* const refp AstVarRef* const refp = new AstVarRef{
= new AstVarRef(nodep->fileline(), varp, nodep->fileline(), varp, VAccess::READ}; // lvalue'ness computed later
VAccess::READ); // lvalue'ness computed later
refp->classOrPackagep(foundp->classOrPackagep()); refp->classOrPackagep(foundp->classOrPackagep());
newp = refp; newp = refp;
} }
@ -2552,8 +2551,8 @@ private:
// iface[vec].modport became CellArrayRef(iface, lsb) // iface[vec].modport became CellArrayRef(iface, lsb)
// Convert back to SelBit(iface, lsb) // Convert back to SelBit(iface, lsb)
UINFO(9, " Array modport to SelBit " << cellarrayrefp << endl); UINFO(9, " Array modport to SelBit " << cellarrayrefp << endl);
newp = new AstSelBit(cellarrayrefp->fileline(), newp, newp = new AstSelBit{cellarrayrefp->fileline(), newp,
cellarrayrefp->selp()->unlinkFrBack()); cellarrayrefp->selp()->unlinkFrBack()};
newp->user3(true); // Don't process again newp->user3(true); // Don't process again
VL_DO_DANGLING(cellarrayrefp->unlinkFrBack(), cellarrayrefp); VL_DO_DANGLING(cellarrayrefp->unlinkFrBack(), cellarrayrefp);
m_ds.m_unlinkedScopep = nullptr; m_ds.m_unlinkedScopep = nullptr;
@ -2564,7 +2563,7 @@ private:
} else if (AstEnumItem* const valuep = VN_CAST(foundp->nodep(), EnumItem)) { } else if (AstEnumItem* const valuep = VN_CAST(foundp->nodep(), EnumItem)) {
if (allowVar) { if (allowVar) {
AstNode* const newp AstNode* const newp
= new AstEnumItemRef(nodep->fileline(), valuep, foundp->classOrPackagep()); = new AstEnumItemRef{nodep->fileline(), valuep, foundp->classOrPackagep()};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
ok = true; ok = true;
@ -2574,7 +2573,7 @@ private:
= VN_CAST(foundp->nodep(), LambdaArgRef)) { = VN_CAST(foundp->nodep(), LambdaArgRef)) {
if (allowVar) { if (allowVar) {
AstNode* const newp AstNode* const newp
= new AstLambdaArgRef(nodep->fileline(), argrefp->name(), false); = new AstLambdaArgRef{nodep->fileline(), argrefp->name(), false};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
ok = true; ok = true;
@ -2618,7 +2617,7 @@ private:
// Create if implicit, and also if error (so only complain once) // Create if implicit, and also if error (so only complain once)
// Else if a scope is allowed, making a signal won't help error cascade // Else if a scope is allowed, making a signal won't help error cascade
AstVarRef* const newp AstVarRef* const newp
= new AstVarRef(nodep->fileline(), nodep->name(), VAccess::READ); = new AstVarRef{nodep->fileline(), nodep->name(), VAccess::READ};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
createImplicitVar(m_curSymp, newp, m_modp, m_modSymp, err); createImplicitVar(m_curSymp, newp, m_modp, m_modSymp, err);
@ -2718,7 +2717,7 @@ private:
if (!m_statep->forPrearray() && !m_statep->forScopeCreation()) { if (!m_statep->forPrearray() && !m_statep->forScopeCreation()) {
if (VN_IS(nodep->dtypep(), IfaceRefDType)) { if (VN_IS(nodep->dtypep(), IfaceRefDType)) {
AstVarRef* const newrefp AstVarRef* const newrefp
= new AstVarRef(nodep->fileline(), nodep->varp(), nodep->access()); = new AstVarRef{nodep->fileline(), nodep->varp(), nodep->access()};
nodep->replaceWith(newrefp); nodep->replaceWith(newrefp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
} }
@ -2743,7 +2742,7 @@ private:
nodep->varScopep(vscp); nodep->varScopep(vscp);
UINFO(7, " Resolved " << nodep << endl); // Also prints taskp UINFO(7, " Resolved " << nodep << endl); // Also prints taskp
AstVarRef* const newvscp AstVarRef* const newvscp
= new AstVarRef(nodep->fileline(), vscp, nodep->access()); = new AstVarRef{nodep->fileline(), vscp, nodep->access()};
nodep->replaceWith(newvscp); nodep->replaceWith(newvscp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
UINFO(9, " new " << newvscp << endl); // Also prints taskp UINFO(9, " new " << newvscp << endl); // Also prints taskp
@ -2800,8 +2799,8 @@ private:
AstNodeFTaskRef* const newftaskp = nodep->cloneTree(false); AstNodeFTaskRef* const newftaskp = nodep->cloneTree(false);
newftaskp->dotted(m_ds.m_dotText); newftaskp->dotted(m_ds.m_dotText);
AstNode* const newp AstNode* const newp
= new AstUnlinkedRef(nodep->fileline(), newftaskp, nodep->name(), = new AstUnlinkedRef{nodep->fileline(), newftaskp, nodep->name(),
m_ds.m_unlinkedScopep->unlinkFrBack()); m_ds.m_unlinkedScopep->unlinkFrBack()};
m_ds.m_unlinkedScopep = nullptr; m_ds.m_unlinkedScopep = nullptr;
m_ds.m_unresolved = false; m_ds.m_unresolved = false;
nodep->replaceWith(newp); nodep->replaceWith(newp);
@ -2815,8 +2814,8 @@ private:
AstNodeExpr* const varEtcp = m_ds.m_dotp->lhsp()->unlinkFrBack(); AstNodeExpr* const varEtcp = m_ds.m_dotp->lhsp()->unlinkFrBack();
AstNodeExpr* argsp = nullptr; AstNodeExpr* argsp = nullptr;
if (nodep->pinsp()) argsp = nodep->pinsp()->unlinkFrBackWithNext(); if (nodep->pinsp()) argsp = nodep->pinsp()->unlinkFrBackWithNext();
AstNode* const newp = new AstMethodCall(nodep->fileline(), varEtcp, VFlagChildDType(), AstNode* const newp = new AstMethodCall{nodep->fileline(), varEtcp, VFlagChildDType{},
nodep->name(), argsp); nodep->name(), argsp};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
return; return;
@ -2897,8 +2896,8 @@ private:
if (v3Global.opt.bboxSys()) { if (v3Global.opt.bboxSys()) {
AstNode* newp; AstNode* newp;
if (VN_IS(nodep, FuncRef)) { if (VN_IS(nodep, FuncRef)) {
newp = new AstConst(nodep->fileline(), AstConst::StringToParse(), newp = new AstConst{nodep->fileline(), AstConst::StringToParse{},
"'0"); "'0"};
} else { } else {
AstNode* outp = nullptr; AstNode* outp = nullptr;
while (nodep->pinsp()) { while (nodep->pinsp()) {
@ -2910,7 +2909,7 @@ private:
} }
outp = AstNode::addNext(outp, addp); outp = AstNode::addNext(outp, addp);
} }
newp = new AstSysIgnore(nodep->fileline(), outp); newp = new AstSysIgnore{nodep->fileline(), outp};
newp->dtypep(nodep->dtypep()); newp->dtypep(nodep->dtypep());
} }
nodep->replaceWith(newp); nodep->replaceWith(newp);
@ -2922,14 +2921,14 @@ private:
} }
} else { } else {
const string suggest = m_statep->suggestSymFallback( const string suggest = m_statep->suggestSymFallback(
dotSymp, nodep->name(), LinkNodeMatcherFTask()); dotSymp, nodep->name(), LinkNodeMatcherFTask{});
nodep->v3error("Can't find definition of task/function: " nodep->v3error("Can't find definition of task/function: "
<< nodep->prettyNameQ() << '\n' << nodep->prettyNameQ() << '\n'
<< (suggest.empty() ? "" : nodep->warnMore() + suggest)); << (suggest.empty() ? "" : nodep->warnMore() + suggest));
} }
} else { } else {
const string suggest = m_statep->suggestSymFallback(dotSymp, nodep->name(), const string suggest = m_statep->suggestSymFallback(dotSymp, nodep->name(),
LinkNodeMatcherFTask()); LinkNodeMatcherFTask{});
nodep->v3error("Can't find definition of " nodep->v3error("Can't find definition of "
<< AstNode::prettyNameQ(baddot) << " in dotted task/function: '" << AstNode::prettyNameQ(baddot) << " in dotted task/function: '"
<< nodep->dotted() + "." + nodep->prettyName() << "'\n" << nodep->dotted() + "." + nodep->prettyName() << "'\n"
@ -2968,7 +2967,7 @@ private:
if (m_ds.m_unresolved && m_ds.m_dotPos == DP_SCOPE) { if (m_ds.m_unresolved && m_ds.m_dotPos == DP_SCOPE) {
AstNodeExpr* const exprp = nodep->bitp()->unlinkFrBack(); AstNodeExpr* const exprp = nodep->bitp()->unlinkFrBack();
AstCellArrayRef* const newp AstCellArrayRef* const newp
= new AstCellArrayRef(nodep->fileline(), nodep->fromp()->name(), exprp); = new AstCellArrayRef{nodep->fileline(), nodep->fromp()->name(), exprp};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
} }
@ -3123,8 +3122,8 @@ private:
AstNode* const itemp = it->second->nodep(); AstNode* const itemp = it->second->nodep();
if (!nodep->findMember(it->first)) { if (!nodep->findMember(it->first)) {
if (AstEnumItem* const aitemp = VN_CAST(itemp, EnumItem)) { if (AstEnumItem* const aitemp = VN_CAST(itemp, EnumItem)) {
AstEnumItemRef* const newp = new AstEnumItemRef( AstEnumItemRef* const newp = new AstEnumItemRef{
aitemp->fileline(), aitemp, it->second->classOrPackagep()); aitemp->fileline(), aitemp, it->second->classOrPackagep()};
UINFO(8, "Class import noderef '" << it->first << "' " << newp << endl); UINFO(8, "Class import noderef '" << it->first << "' " << newp << endl);
nodep->addMembersp(newp); nodep->addMembersp(newp);
} }

View File

@ -769,7 +769,7 @@ public:
// For each node, record the critical path cost from the start // For each node, record the critical path cost from the start
// of the graph through the end of the node. // of the graph through the end of the node.
std::unordered_map<const V3GraphVertex*, uint32_t> critPaths; std::unordered_map<const V3GraphVertex*, uint32_t> critPaths;
GraphStreamUnordered serialize(m_graphp); GraphStreamUnordered serialize{m_graphp};
for (const V3GraphVertex* vertexp; (vertexp = serialize.nextp());) { for (const V3GraphVertex* vertexp; (vertexp = serialize.nextp());) {
++m_vertexCount; ++m_vertexCount;
uint32_t cpCostToHere = 0; uint32_t cpCostToHere = 0;
@ -1110,7 +1110,7 @@ private:
} }
public: public:
static void selfTest() { PartPropagateCpSelfTest().go(); } static void selfTest() { PartPropagateCpSelfTest{}.go(); }
}; };
// Merge edges from a LogicMtask. // Merge edges from a LogicMtask.
@ -1731,9 +1731,9 @@ private:
V3Graph mtasks; V3Graph mtasks;
LogicMTask* lastp = nullptr; LogicMTask* lastp = nullptr;
for (unsigned i = 0; i < chain_len; ++i) { for (unsigned i = 0; i < chain_len; ++i) {
LogicMTask* const mtp = new LogicMTask(&mtasks, nullptr); LogicMTask* const mtp = new LogicMTask{&mtasks, nullptr};
mtp->setCost(1); mtp->setCost(1);
if (lastp) new MTaskEdge(&mtasks, lastp, mtp, 1); if (lastp) new MTaskEdge{&mtasks, lastp, mtp, 1};
lastp = mtp; lastp = mtp;
} }
partInitCriticalPaths(&mtasks); partInitCriticalPaths(&mtasks);
@ -1741,12 +1741,12 @@ private:
// Since slowAsserts mode is *expected* to cause N^2 runtime, and the // Since slowAsserts mode is *expected* to cause N^2 runtime, and the
// intent of this test is to demonstrate better-than-N^2 runtime, disable // intent of this test is to demonstrate better-than-N^2 runtime, disable
// slowAsserts. // slowAsserts.
PartContraction ec(&mtasks, PartContraction ec{&mtasks,
// Any CP limit >chain_len should work: // Any CP limit >chain_len should work:
chain_len * 2, false /* slowAsserts */); chain_len * 2, false /* slowAsserts */};
ec.go(); ec.go();
PartParallelismEst check(&mtasks); PartParallelismEst check{&mtasks};
check.traverse(); check.traverse();
const uint64_t endUsecs = V3Os::timeUsecs(); const uint64_t endUsecs = V3Os::timeUsecs();
@ -1780,26 +1780,26 @@ private:
static void selfTestX() { static void selfTestX() {
// NOTE: To get a dot file run with --debugi-V3Partition 4 or more. // NOTE: To get a dot file run with --debugi-V3Partition 4 or more.
V3Graph mtasks; V3Graph mtasks;
LogicMTask* const centerp = new LogicMTask(&mtasks, nullptr); LogicMTask* const centerp = new LogicMTask{&mtasks, nullptr};
centerp->setCost(1); centerp->setCost(1);
unsigned i; unsigned i;
for (i = 0; i < 50; ++i) { for (i = 0; i < 50; ++i) {
LogicMTask* const mtp = new LogicMTask(&mtasks, nullptr); LogicMTask* const mtp = new LogicMTask{&mtasks, nullptr};
mtp->setCost(1); mtp->setCost(1);
// Edge from every input -> centerp // Edge from every input -> centerp
new MTaskEdge(&mtasks, mtp, centerp, 1); new MTaskEdge{&mtasks, mtp, centerp, 1};
} }
for (i = 0; i < 50; ++i) { for (i = 0; i < 50; ++i) {
LogicMTask* const mtp = new LogicMTask(&mtasks, nullptr); LogicMTask* const mtp = new LogicMTask{&mtasks, nullptr};
mtp->setCost(1); mtp->setCost(1);
// Edge from centerp -> every output // Edge from centerp -> every output
new MTaskEdge(&mtasks, centerp, mtp, 1); new MTaskEdge{&mtasks, centerp, mtp, 1};
} }
partInitCriticalPaths(&mtasks); partInitCriticalPaths(&mtasks);
PartContraction(&mtasks, 20, true).go(); PartContraction{&mtasks, 20, true}.go();
PartParallelismEst check(&mtasks); PartParallelismEst check{&mtasks};
check.traverse(); check.traverse();
// Checking exact values here is maybe overly precise. What we're // Checking exact values here is maybe overly precise. What we're
@ -2033,7 +2033,7 @@ public:
// Rank the graph. DGS is faster than V3GraphAlg's recursive rank, and also allows us to // Rank the graph. DGS is faster than V3GraphAlg's recursive rank, and also allows us to
// set up the OrderLogicVertex -> LogicMTask map at the same time. // set up the OrderLogicVertex -> LogicMTask map at the same time.
{ {
GraphStreamUnordered serialize(m_mtasksp); GraphStreamUnordered serialize{m_mtasksp};
while (LogicMTask* const mtaskp while (LogicMTask* const mtaskp
= const_cast<LogicMTask*>(static_cast<const LogicMTask*>(serialize.nextp()))) { = const_cast<LogicMTask*>(static_cast<const LogicMTask*>(serialize.nextp()))) {
// Compute and assign rank // Compute and assign rank
@ -2382,7 +2382,7 @@ public:
// Pack an MTasks from given graph into m_nThreads threads, return the schedule. // Pack an MTasks from given graph into m_nThreads threads, return the schedule.
const ThreadSchedule pack(const V3Graph& mtaskGraph) { const ThreadSchedule pack(const V3Graph& mtaskGraph) {
// The result // The result
ThreadSchedule schedule(m_nThreads); ThreadSchedule schedule{m_nThreads};
// Time each thread is occupied until // Time each thread is occupied until
std::vector<uint32_t> busyUntil(m_nThreads, 0); std::vector<uint32_t> busyUntil(m_nThreads, 0);
@ -2475,22 +2475,22 @@ public:
// SELF TEST // SELF TEST
static void selfTest() { static void selfTest() {
V3Graph graph; V3Graph graph;
ExecMTask* const t0 = new ExecMTask(&graph, nullptr, 0); ExecMTask* const t0 = new ExecMTask{&graph, nullptr, 0};
t0->cost(1000); t0->cost(1000);
t0->priority(1100); t0->priority(1100);
ExecMTask* const t1 = new ExecMTask(&graph, nullptr, 1); ExecMTask* const t1 = new ExecMTask{&graph, nullptr, 1};
t1->cost(100); t1->cost(100);
t1->priority(100); t1->priority(100);
ExecMTask* const t2 = new ExecMTask(&graph, nullptr, 2); ExecMTask* const t2 = new ExecMTask{&graph, nullptr, 2};
t2->cost(100); t2->cost(100);
t2->priority(100); t2->priority(100);
new V3GraphEdge(&graph, t0, t1, 1); new V3GraphEdge{&graph, t0, t1, 1};
new V3GraphEdge(&graph, t0, t2, 1); new V3GraphEdge{&graph, t0, t2, 1};
PartPackMTasks packer(2, // Threads PartPackMTasks packer{2, // Threads
3, // Sandbag numerator 3, // Sandbag numerator
10); // Sandbag denom 10}; // Sandbag denom
const ThreadSchedule& schedule = packer.pack(graph); const ThreadSchedule& schedule = packer.pack(graph);
UASSERT_SELFTEST(size_t, schedule.threads.size(), 2); UASSERT_SELFTEST(size_t, schedule.threads.size(), 2);
@ -2748,7 +2748,7 @@ void V3Partition::go(V3Graph* mtasksp) {
// Merge nodes that could present data hazards; see comment within. // Merge nodes that could present data hazards; see comment within.
{ {
PartFixDataHazards(m_orderGraphp, mtasksp).go(); PartFixDataHazards{m_orderGraphp, mtasksp}.go();
V3Partition::debugMTaskGraphStats(mtasksp, "hazards"); V3Partition::debugMTaskGraphStats(mtasksp, "hazards");
hashGraphDebug(mtasksp, "mtasksp after fixDataHazards()"); hashGraphDebug(mtasksp, "mtasksp after fixDataHazards()");
} }
@ -2791,10 +2791,10 @@ void V3Partition::go(V3Graph* mtasksp) {
// Some tests disable this, hence the test on threadsCoarsen(). // Some tests disable this, hence the test on threadsCoarsen().
// Coarsening is always enabled in production. // Coarsening is always enabled in production.
if (v3Global.opt.threadsCoarsen()) { if (v3Global.opt.threadsCoarsen()) {
PartContraction(mtasksp, cpLimit, PartContraction{mtasksp, cpLimit,
// --debugPartition is used by tests // --debugPartition is used by tests
// to enable slow assertions. // to enable slow assertions.
v3Global.opt.debugPartition()) v3Global.opt.debugPartition()}
.go(); .go();
V3Partition::debugMTaskGraphStats(mtasksp, "contraction"); V3Partition::debugMTaskGraphStats(mtasksp, "contraction");
} }
@ -3011,7 +3011,7 @@ static void finalizeCosts(V3Graph* execMTaskGraphp) {
UINFO(6, "Removing zero-cost " << mtp->name() << endl); UINFO(6, "Removing zero-cost " << mtp->name() << endl);
for (V3GraphEdge* inp = mtp->inBeginp(); inp; inp = inp->inNextp()) { for (V3GraphEdge* inp = mtp->inBeginp(); inp; inp = inp->inNextp()) {
for (V3GraphEdge* outp = mtp->outBeginp(); outp; outp = outp->outNextp()) { for (V3GraphEdge* outp = mtp->outBeginp(); outp; outp = outp->outNextp()) {
new V3GraphEdge(execMTaskGraphp, inp->fromp(), outp->top(), 1); new V3GraphEdge{execMTaskGraphp, inp->fromp(), outp->top(), 1};
} }
} }
VL_DO_DANGLING(mtp->unlinkDelete(execMTaskGraphp), mtp); VL_DO_DANGLING(mtp->unlinkDelete(execMTaskGraphp), mtp);
@ -3052,7 +3052,7 @@ static void addMTaskToFunction(const ThreadSchedule& schedule, const uint32_t th
// Helper function to make the code a bit more legible // Helper function to make the code a bit more legible
const auto addStrStmt = [=](const string& stmt) -> void { // const auto addStrStmt = [=](const string& stmt) -> void { //
funcp->addStmtsp(new AstCStmt(fl, stmt)); funcp->addStmtsp(new AstCStmt{fl, stmt});
}; };
if (const uint32_t nDependencies = schedule.crossThreadDependencies(mtaskp)) { if (const uint32_t nDependencies = schedule.crossThreadDependencies(mtaskp)) {
@ -3061,8 +3061,8 @@ static void addMTaskToFunction(const ThreadSchedule& schedule, const uint32_t th
const string name = "__Vm_mtaskstate_" + cvtToStr(mtaskp->id()); const string name = "__Vm_mtaskstate_" + cvtToStr(mtaskp->id());
AstBasicDType* const mtaskStateDtypep AstBasicDType* const mtaskStateDtypep
= v3Global.rootp()->typeTablep()->findBasicDType(fl, VBasicDTypeKwd::MTASKSTATE); = v3Global.rootp()->typeTablep()->findBasicDType(fl, VBasicDTypeKwd::MTASKSTATE);
AstVar* const varp = new AstVar(fl, VVarType::MODULETEMP, name, mtaskStateDtypep); AstVar* const varp = new AstVar{fl, VVarType::MODULETEMP, name, mtaskStateDtypep};
varp->valuep(new AstConst(fl, nDependencies)); varp->valuep(new AstConst{fl, nDependencies});
varp->protect(false); // Do not protect as we still have references in AstText varp->protect(false); // Do not protect as we still have references in AstText
modp->addStmtsp(varp); modp->addStmtsp(varp);
// For now, reference is still via text bashing // For now, reference is still via text bashing
@ -3124,7 +3124,7 @@ static const std::vector<AstCFunc*> createThreadFunctions(const ThreadSchedule&
if (thread.empty()) continue; if (thread.empty()) continue;
const uint32_t threadId = schedule.threadId(thread.front()); const uint32_t threadId = schedule.threadId(thread.front());
const string name{"__Vthread__" + tag + "__" + cvtToStr(threadId)}; const string name{"__Vthread__" + tag + "__" + cvtToStr(threadId)};
AstCFunc* const funcp = new AstCFunc(fl, name, nullptr, "void"); AstCFunc* const funcp = new AstCFunc{fl, name, nullptr, "void"};
modp->addStmtsp(funcp); modp->addStmtsp(funcp);
funcps.push_back(funcp); funcps.push_back(funcp);
funcp->isStatic(true); // Uses void self pointer, so static and hand rolled funcp->isStatic(true); // Uses void self pointer, so static and hand rolled
@ -3166,10 +3166,10 @@ static void addThreadStartToExecGraph(AstExecGraph* const execGraphp,
// Add thread function invocations to execGraph // Add thread function invocations to execGraph
const auto addStrStmt = [=](const string& stmt) -> void { // const auto addStrStmt = [=](const string& stmt) -> void { //
execGraphp->addStmtsp(new AstCStmt(fl, stmt)); execGraphp->addStmtsp(new AstCStmt{fl, stmt});
}; };
const auto addTextStmt = [=](const string& text) -> void { const auto addTextStmt = [=](const string& text) -> void {
execGraphp->addStmtsp(new AstText(fl, text, /* tracking: */ true)); execGraphp->addStmtsp(new AstText{fl, text, /* tracking: */ true});
}; };
addStrStmt("vlSymsp->__Vm_even_cycle__" + tag + " = !vlSymsp->__Vm_even_cycle__" + tag addStrStmt("vlSymsp->__Vm_even_cycle__" + tag + " = !vlSymsp->__Vm_even_cycle__" + tag
@ -3181,11 +3181,11 @@ static void addThreadStartToExecGraph(AstExecGraph* const execGraphp,
if (i != last) { if (i != last) {
// The first N-1 will run on the thread pool. // The first N-1 will run on the thread pool.
addTextStmt("vlSymsp->__Vm_threadPoolp->workerp(" + cvtToStr(i) + ")->addTask("); addTextStmt("vlSymsp->__Vm_threadPoolp->workerp(" + cvtToStr(i) + ")->addTask(");
execGraphp->addStmtsp(new AstAddrOfCFunc(fl, funcp)); execGraphp->addStmtsp(new AstAddrOfCFunc{fl, funcp});
addTextStmt(", vlSelf, vlSymsp->__Vm_even_cycle__" + tag + ");\n"); addTextStmt(", vlSelf, vlSymsp->__Vm_even_cycle__" + tag + ");\n");
} else { } else {
// The last will run on the main thread. // The last will run on the main thread.
AstCCall* const callp = new AstCCall(fl, funcp); AstCCall* const callp = new AstCCall{fl, funcp};
callp->dtypeSetVoid(); callp->dtypeSetVoid();
callp->argTypes("vlSelf, vlSymsp->__Vm_even_cycle__" + tag); callp->argTypes("vlSelf, vlSymsp->__Vm_even_cycle__" + tag);
execGraphp->addStmtsp(callp->makeStmt()); execGraphp->addStmtsp(callp->makeStmt());
@ -3203,7 +3203,7 @@ static void implementExecGraph(AstExecGraph* const execGraphp) {
// Schedule the mtasks: statically associate each mtask with a thread, // Schedule the mtasks: statically associate each mtask with a thread,
// and determine the order in which each thread will runs its mtasks. // and determine the order in which each thread will runs its mtasks.
const ThreadSchedule& schedule = PartPackMTasks().pack(*execGraphp->depGraphp()); const ThreadSchedule& schedule = PartPackMTasks{}.pack(*execGraphp->depGraphp());
// Create a function to be run by each thread. Note this moves all AstMTaskBody nodes form the // Create a function to be run by each thread. Note this moves all AstMTaskBody nodes form the
// AstExecGrap into the AstCFunc created // AstExecGrap into the AstCFunc created

View File

@ -163,7 +163,7 @@ private:
} }
} }
TaskFTaskVertex* getFTaskVertex(AstNodeFTask* nodep) { TaskFTaskVertex* getFTaskVertex(AstNodeFTask* nodep) {
if (!nodep->user4p()) nodep->user4p(new TaskFTaskVertex(&m_callGraph, nodep)); if (!nodep->user4p()) nodep->user4p(new TaskFTaskVertex{&m_callGraph, nodep});
return static_cast<TaskFTaskVertex*>(nodep->user4u().toGraphVertex()); return static_cast<TaskFTaskVertex*>(nodep->user4u().toGraphVertex());
} }
@ -204,7 +204,7 @@ private:
} }
// We make multiple edges if a task is called multiple times from another task. // We make multiple edges if a task is called multiple times from another task.
UASSERT_OBJ(nodep->taskp(), nodep, "Unlinked task"); UASSERT_OBJ(nodep->taskp(), nodep, "Unlinked task");
new TaskEdge(&m_callGraph, m_curVxp, getFTaskVertex(nodep->taskp())); new TaskEdge{&m_callGraph, m_curVxp, getFTaskVertex(nodep->taskp())};
} }
void visit(AstNodeFTask* nodep) override { void visit(AstNodeFTask* nodep) override {
UINFO(9, " TASK " << nodep << endl); UINFO(9, " TASK " << nodep << endl);
@ -276,7 +276,7 @@ private:
public: public:
// CONSTRUCTORS // CONSTRUCTORS
explicit TaskStateVisitor(AstNetlist* nodep) { explicit TaskStateVisitor(AstNetlist* nodep) {
m_curVxp = new TaskCodeVertex(&m_callGraph); m_curVxp = new TaskCodeVertex{&m_callGraph};
AstNode::user3ClearTree(); AstNode::user3ClearTree();
AstNode::user4ClearTree(); AstNode::user4ClearTree();
// //
@ -369,20 +369,20 @@ private:
// METHODS // METHODS
AstVarScope* createFuncVar(AstCFunc* funcp, const string& name, AstVar* examplep) { AstVarScope* createFuncVar(AstCFunc* funcp, const string& name, AstVar* examplep) {
AstVar* const newvarp = new AstVar(funcp->fileline(), VVarType::BLOCKTEMP, name, examplep); AstVar* const newvarp = new AstVar{funcp->fileline(), VVarType::BLOCKTEMP, name, examplep};
newvarp->funcLocal(true); newvarp->funcLocal(true);
funcp->addInitsp(newvarp); funcp->addInitsp(newvarp);
AstVarScope* const newvscp = new AstVarScope(funcp->fileline(), m_scopep, newvarp); AstVarScope* const newvscp = new AstVarScope{funcp->fileline(), m_scopep, newvarp};
m_scopep->addVarsp(newvscp); m_scopep->addVarsp(newvscp);
return newvscp; return newvscp;
} }
AstVarScope* createInputVar(AstCFunc* funcp, const string& name, VBasicDTypeKwd kwd) { AstVarScope* createInputVar(AstCFunc* funcp, const string& name, VBasicDTypeKwd kwd) {
AstVar* const newvarp AstVar* const newvarp
= new AstVar(funcp->fileline(), VVarType::BLOCKTEMP, name, funcp->findBasicDType(kwd)); = new AstVar{funcp->fileline(), VVarType::BLOCKTEMP, name, funcp->findBasicDType(kwd)};
newvarp->funcLocal(true); newvarp->funcLocal(true);
newvarp->direction(VDirection::INPUT); newvarp->direction(VDirection::INPUT);
funcp->addArgsp(newvarp); funcp->addArgsp(newvarp);
AstVarScope* const newvscp = new AstVarScope(funcp->fileline(), m_scopep, newvarp); AstVarScope* const newvscp = new AstVarScope{funcp->fileline(), m_scopep, newvarp};
m_scopep->addVarsp(newvscp); m_scopep->addVarsp(newvscp);
return newvscp; return newvscp;
} }
@ -425,7 +425,7 @@ private:
AstNode* const newbodysp AstNode* const newbodysp
= AstNode::cloneTreeNull(refp->taskp()->stmtsp(), true); // Maybe nullptr = AstNode::cloneTreeNull(refp->taskp()->stmtsp(), true); // Maybe nullptr
AstNode* const beginp AstNode* const beginp
= new AstComment(refp->fileline(), string("Function: ") + refp->name(), true); = new AstComment{refp->fileline(), string("Function: ") + refp->name(), true};
if (newbodysp) beginp->addNext(newbodysp); if (newbodysp) beginp->addNext(newbodysp);
if (debug() >= 9) beginp->dumpTreeAndNext(cout, "-newbegi:"); if (debug() >= 9) beginp->dumpTreeAndNext(cout, "-newbegi:");
// //
@ -478,9 +478,9 @@ private:
AstVarScope* const tempvscp AstVarScope* const tempvscp
= createVarScope(portp, namePrefix + "__" + portp->shortName()); = createVarScope(portp, namePrefix + "__" + portp->shortName());
portp->user2p(tempvscp); portp->user2p(tempvscp);
AstAssign* const assp = new AstAssign( AstAssign* const assp = new AstAssign{
pinp->fileline(), pinp, pinp->fileline(), pinp,
new AstVarRef(tempvscp->fileline(), tempvscp, VAccess::READ)); new AstVarRef{tempvscp->fileline(), tempvscp, VAccess::READ}};
assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ, assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ,
true); // Ok if in <= block true); // Ok if in <= block
// Put assignment BEHIND of all other statements // Put assignment BEHIND of all other statements
@ -490,9 +490,9 @@ private:
AstVarScope* const inVscp AstVarScope* const inVscp
= createVarScope(portp, namePrefix + "__" + portp->shortName()); = createVarScope(portp, namePrefix + "__" + portp->shortName());
portp->user2p(inVscp); portp->user2p(inVscp);
AstAssign* const assp = new AstAssign( AstAssign* const assp = new AstAssign{
pinp->fileline(), pinp->fileline(),
new AstVarRef(inVscp->fileline(), inVscp, VAccess::WRITE), pinp); new AstVarRef{inVscp->fileline(), inVscp, VAccess::WRITE}, pinp};
assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ, assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ,
true); // Ok if in <= block true); // Ok if in <= block
// Put assignment in FRONT of all other statements // Put assignment in FRONT of all other statements
@ -542,20 +542,20 @@ private:
UASSERT_OBJ(cfuncp, refp, "No non-inline task associated with this task call?"); UASSERT_OBJ(cfuncp, refp, "No non-inline task associated with this task call?");
// //
AstNode* const beginp AstNode* const beginp
= new AstComment(refp->fileline(), string("Function: ") + refp->name(), true); = new AstComment{refp->fileline(), string("Function: ") + refp->name(), true};
AstNodeCCall* ccallp; AstNodeCCall* ccallp;
if (VN_IS(refp, New)) { if (VN_IS(refp, New)) {
AstCNew* const cnewp = new AstCNew(refp->fileline(), cfuncp); AstCNew* const cnewp = new AstCNew{refp->fileline(), cfuncp};
cnewp->dtypep(refp->dtypep()); cnewp->dtypep(refp->dtypep());
ccallp = cnewp; ccallp = cnewp;
// Parent AstNew will replace with this CNew // Parent AstNew will replace with this CNew
cnewpr = cnewp; cnewpr = cnewp;
} else if (const AstMethodCall* const mrefp = VN_CAST(refp, MethodCall)) { } else if (const AstMethodCall* const mrefp = VN_CAST(refp, MethodCall)) {
ccallp = new AstCMethodCall(refp->fileline(), mrefp->fromp()->unlinkFrBack(), cfuncp); ccallp = new AstCMethodCall{refp->fileline(), mrefp->fromp()->unlinkFrBack(), cfuncp};
ccallp->dtypeSetVoid(); ccallp->dtypeSetVoid();
beginp->addNext(ccallp->makeStmt()); beginp->addNext(ccallp->makeStmt());
} else { } else {
ccallp = new AstCCall(refp->fileline(), cfuncp); ccallp = new AstCCall{refp->fileline(), cfuncp};
ccallp->dtypeSetVoid(); ccallp->dtypeSetVoid();
beginp->addNext(ccallp->makeStmt()); beginp->addNext(ccallp->makeStmt());
} }
@ -598,10 +598,10 @@ private:
AstVarScope* const newvscp AstVarScope* const newvscp
= createVarScope(portp, namePrefix + "__" + portp->shortName()); = createVarScope(portp, namePrefix + "__" + portp->shortName());
portp->user2p(newvscp); portp->user2p(newvscp);
pinp->replaceWith(new AstVarRef(newvscp->fileline(), newvscp, VAccess::WRITE)); pinp->replaceWith(new AstVarRef{newvscp->fileline(), newvscp, VAccess::WRITE});
AstAssign* const assp = new AstAssign( AstAssign* const assp = new AstAssign{
pinp->fileline(), pinp, pinp->fileline(), pinp,
new AstVarRef(newvscp->fileline(), newvscp, VAccess::READ)); new AstVarRef{newvscp->fileline(), newvscp, VAccess::READ}};
assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ, assp->fileline()->modifyWarnOff(V3ErrorCode::BLKSEQ,
true); // Ok if in <= block true); // Ok if in <= block
// Put assignment BEHIND of all other statements // Put assignment BEHIND of all other statements
@ -619,8 +619,8 @@ private:
UASSERT_OBJ(snp, refp, "Missing scoping context"); UASSERT_OBJ(snp, refp, "Missing scoping context");
ccallp->addArgsp(snp); ccallp->addArgsp(snp);
// __Vfilenamep // __Vfilenamep
ccallp->addArgsp(new AstCExpr(refp->fileline(), ccallp->addArgsp(new AstCExpr{refp->fileline(),
"\"" + refp->fileline()->filename() + "\"", 64, true)); "\"" + refp->fileline()->filename() + "\"", 64, true});
// __Vlineno // __Vlineno
ccallp->addArgsp(new AstConst(refp->fileline(), refp->fileline()->lineno())); ccallp->addArgsp(new AstConst(refp->fileline(), refp->fileline()->lineno()));
} }
@ -635,7 +635,7 @@ private:
ccallp->addArgsp(exprp); ccallp->addArgsp(exprp);
} }
if (outvscp) ccallp->addArgsp(new AstVarRef(refp->fileline(), outvscp, VAccess::WRITE)); if (outvscp) ccallp->addArgsp(new AstVarRef{refp->fileline(), outvscp, VAccess::WRITE});
if (debug() >= 9) beginp->dumpTreeAndNext(cout, "-nitask: "); if (debug() >= 9) beginp->dumpTreeAndNext(cout, "-nitask: ");
return beginp; return beginp;
@ -668,7 +668,7 @@ private:
static AstNode* createDpiTemp(AstVar* portp, const string& suffix) { static AstNode* createDpiTemp(AstVar* portp, const string& suffix) {
const string stmt = portp->dpiTmpVarType(portp->name() + suffix) + ";\n"; const string stmt = portp->dpiTmpVarType(portp->name() + suffix) + ";\n";
return new AstCStmt(portp->fileline(), stmt); return new AstCStmt{portp->fileline(), stmt};
} }
void unlinkAndClone(AstNodeFTask* funcp, AstNode* nodep, bool withNext) { void unlinkAndClone(AstNodeFTask* funcp, AstNode* nodep, bool withNext) {
@ -692,7 +692,7 @@ private:
static AstNode* createAssignInternalToDpi(AstVar* portp, bool isPtr, const string& frSuffix, static AstNode* createAssignInternalToDpi(AstVar* portp, bool isPtr, const string& frSuffix,
const string& toSuffix) { const string& toSuffix) {
const string stmt = V3Task::assignInternalToDpi(portp, isPtr, frSuffix, toSuffix); const string stmt = V3Task::assignInternalToDpi(portp, isPtr, frSuffix, toSuffix);
return new AstCStmt(portp->fileline(), stmt); return new AstCStmt{portp->fileline(), stmt};
} }
AstNode* createAssignDpiToInternal(AstVarScope* portvscp, const string& frName) { AstNode* createAssignDpiToInternal(AstVarScope* portvscp, const string& frName) {
@ -721,7 +721,7 @@ private:
AstNode* newp = nullptr; AstNode* newp = nullptr;
const int widthWords = portp->basicp()->widthWords(); const int widthWords = portp->basicp()->widthWords();
for (int i = 0; i < total; ++i) { for (int i = 0; i < total; ++i) {
AstNodeExpr* srcp = new AstVarRef(portvscp->fileline(), portvscp, VAccess::WRITE); AstNodeExpr* srcp = new AstVarRef{portvscp->fileline(), portvscp, VAccess::WRITE};
// extract a scalar from multi-dimensional array (internal format) // extract a scalar from multi-dimensional array (internal format)
for (auto&& dimStride : dimStrides) { for (auto&& dimStride : dimStrides) {
const size_t dimIdx = (i / dimStride.second) % dimStride.first->elementsConst(); const size_t dimIdx = (i / dimStride.second) % dimStride.first->elementsConst();
@ -730,12 +730,12 @@ private:
AstNode* stmtp = nullptr; AstNode* stmtp = nullptr;
// extract a scalar from DPI temporary var that is scalar or 1D array // extract a scalar from DPI temporary var that is scalar or 1D array
if (useSetWSvlv) { if (useSetWSvlv) {
AstNode* const linesp = new AstText(portvscp->fileline(), frstmt + ket); AstNode* const linesp = new AstText{portvscp->fileline(), frstmt + ket};
linesp->addNext(srcp); linesp->addNext(srcp);
linesp->addNext( linesp->addNext(
new AstText(portvscp->fileline(), new AstText{portvscp->fileline(),
"," + frName + " + " + cvtToStr(i * widthWords) + ");\n")); "," + frName + " + " + cvtToStr(i * widthWords) + ");\n"});
stmtp = new AstCStmt(portvscp->fileline(), linesp); stmtp = new AstCStmt{portvscp->fileline(), linesp};
} else { } else {
string from = frstmt; string from = frstmt;
if (!dimStrides.empty()) { if (!dimStrides.empty()) {
@ -744,10 +744,10 @@ private:
from += "[" + cvtToStr(i * coef) + "]"; from += "[" + cvtToStr(i * coef) + "]";
} }
from += ket; from += ket;
AstNodeExpr* const rhsp = new AstSel( AstNodeExpr* const rhsp = new AstSel{
portp->fileline(), new AstCExpr(portp->fileline(), from, cwidth, false), 0, portp->fileline(), new AstCExpr{portp->fileline(), from, cwidth, false}, 0,
portp->width()); portp->width()};
stmtp = new AstAssign(portp->fileline(), srcp, rhsp); stmtp = new AstAssign{portp->fileline(), srcp, rhsp};
} }
if (i > 0) { if (i > 0) {
newp->addNext(stmtp); newp->addNext(stmtp);
@ -760,8 +760,8 @@ private:
AstCFunc* makeDpiExportDispatcher(AstNodeFTask* nodep, AstVar* rtnvarp) { AstCFunc* makeDpiExportDispatcher(AstNodeFTask* nodep, AstVar* rtnvarp) {
const char* const tmpSuffixp = V3Task::dpiTemporaryVarSuffix(); const char* const tmpSuffixp = V3Task::dpiTemporaryVarSuffix();
AstCFunc* const funcp = new AstCFunc(nodep->fileline(), nodep->cname(), m_scopep, AstCFunc* const funcp = new AstCFunc{nodep->fileline(), nodep->cname(), m_scopep,
(rtnvarp ? rtnvarp->dpiArgType(true, true) : "")); (rtnvarp ? rtnvarp->dpiArgType(true, true) : "")};
funcp->dpiExportDispatcher(true); funcp->dpiExportDispatcher(true);
funcp->dpiContext(nodep->dpiContext()); funcp->dpiContext(nodep->dpiContext());
funcp->dontCombine(true); funcp->dontCombine(true);
@ -797,7 +797,7 @@ private:
+ ")(VerilatedScope::exportFind(__Vscopep, __Vfuncnum));\n"; // Can't use + ")(VerilatedScope::exportFind(__Vscopep, __Vfuncnum));\n"; // Can't use
// static_cast // static_cast
// If __Vcb is null the exportFind function throws and error // If __Vcb is null the exportFind function throws and error
funcp->addStmtsp(new AstCStmt(nodep->fileline(), stmt)); funcp->addStmtsp(new AstCStmt{nodep->fileline(), stmt});
} }
// Convert input/inout DPI arguments to Internal types // Convert input/inout DPI arguments to Internal types
@ -812,7 +812,7 @@ private:
// SAME CODE BELOW // SAME CODE BELOW
args += ", "; args += ", ";
if (args != "") { if (args != "") {
argnodesp = argnodesp->addNext(new AstText(portp->fileline(), args, true)); argnodesp = argnodesp->addNext(new AstText{portp->fileline(), args, true});
args = ""; args = "";
} }
AstVarScope* const outvscp AstVarScope* const outvscp
@ -821,8 +821,8 @@ private:
outvscp->varp()->protect(false); outvscp->varp()->protect(false);
portp->protect(false); portp->protect(false);
AstVarRef* const refp AstVarRef* const refp
= new AstVarRef(portp->fileline(), outvscp, = new AstVarRef{portp->fileline(), outvscp,
portp->isWritable() ? VAccess::WRITE : VAccess::READ); portp->isWritable() ? VAccess::WRITE : VAccess::READ};
argnodesp = argnodesp->addNext(refp); argnodesp = argnodesp->addNext(refp);
if (portp->isNonOutput()) { if (portp->isNonOutput()) {
@ -843,14 +843,14 @@ private:
// SAME CODE ABOVE // SAME CODE ABOVE
args += ", "; args += ", ";
if (args != "") { if (args != "") {
argnodesp = argnodesp->addNext(new AstText(portp->fileline(), args, true)); argnodesp = argnodesp->addNext(new AstText{portp->fileline(), args, true});
args = ""; args = "";
} }
AstVarScope* const outvscp = createFuncVar(funcp, portp->name() + tmpSuffixp, portp); AstVarScope* const outvscp = createFuncVar(funcp, portp->name() + tmpSuffixp, portp);
// No information exposure; is already visible in import/export func template // No information exposure; is already visible in import/export func template
outvscp->varp()->protect(false); outvscp->varp()->protect(false);
AstVarRef* const refp = new AstVarRef( AstVarRef* const refp = new AstVarRef{
portp->fileline(), outvscp, portp->isWritable() ? VAccess::WRITE : VAccess::READ); portp->fileline(), outvscp, portp->isWritable() ? VAccess::WRITE : VAccess::READ};
argnodesp = argnodesp->addNext(refp); argnodesp = argnodesp->addNext(refp);
} }
@ -858,10 +858,10 @@ private:
// Add the variables referenced as VarRef's so that lifetime analysis // Add the variables referenced as VarRef's so that lifetime analysis
// doesn't rip up the variables on us // doesn't rip up the variables on us
args += ");\n"; args += ");\n";
AstCStmt* const newp = new AstCStmt(nodep->fileline(), "(*__Vcb)("); AstCStmt* const newp = new AstCStmt{nodep->fileline(), "(*__Vcb)("};
newp->addExprsp(argnodesp); newp->addExprsp(argnodesp);
VL_DANGLING(argnodesp); VL_DANGLING(argnodesp);
newp->addExprsp(new AstText(nodep->fileline(), args, true)); newp->addExprsp(new AstText{nodep->fileline(), args, true});
funcp->addStmtsp(newp); funcp->addStmtsp(newp);
} }
@ -879,7 +879,7 @@ private:
funcp->addStmtsp(createAssignInternalToDpi(rtnvarp, false, tmpSuffixp, "")); funcp->addStmtsp(createAssignInternalToDpi(rtnvarp, false, tmpSuffixp, ""));
string stmt = "return " + rtnvarp->name(); string stmt = "return " + rtnvarp->name();
stmt += rtnvarp->basicp()->isDpiPrimitive() ? ";\n" : "[0];\n"; stmt += rtnvarp->basicp()->isDpiPrimitive() ? ";\n" : "[0];\n";
funcp->addStmtsp(new AstCStmt(nodep->fileline(), stmt)); funcp->addStmtsp(new AstCStmt{nodep->fileline(), stmt});
} }
makePortList(nodep, funcp); makePortList(nodep, funcp);
return funcp; return funcp;
@ -894,7 +894,7 @@ private:
const string rtnType = rtnvarp ? rtnvarp->dpiArgType(true, true) const string rtnType = rtnvarp ? rtnvarp->dpiArgType(true, true)
: nodep->dpiTask() ? "int" : nodep->dpiTask() ? "int"
: ""; : "";
AstCFunc* const funcp = new AstCFunc(nodep->fileline(), nodep->cname(), m_scopep, rtnType); AstCFunc* const funcp = new AstCFunc{nodep->fileline(), nodep->cname(), m_scopep, rtnType};
funcp->dpiContext(nodep->dpiContext()); funcp->dpiContext(nodep->dpiContext());
funcp->dpiImportPrototype(true); funcp->dpiImportPrototype(true);
funcp->dontCombine(true); funcp->dontCombine(true);
@ -997,7 +997,7 @@ private:
// At least put them into the module's CTOR as static? // At least put them into the module's CTOR as static?
const string propName = portp->name() + "__Vopenprops"; const string propName = portp->name() + "__Vopenprops";
const string propCode = portp->vlPropDecl(propName); const string propCode = portp->vlPropDecl(propName);
cfuncp->addStmtsp(new AstCStmt(portp->fileline(), propCode)); cfuncp->addStmtsp(new AstCStmt{portp->fileline(), propCode});
// //
// At runtime we need the svOpenArrayHandle to // At runtime we need the svOpenArrayHandle to
// point to this task & thread's data, in addition // point to this task & thread's data, in addition
@ -1007,7 +1007,7 @@ private:
= ("VerilatedDpiOpenVar " = ("VerilatedDpiOpenVar "
// NOLINTNEXTLINE(performance-inefficient-string-concatenation) // NOLINTNEXTLINE(performance-inefficient-string-concatenation)
+ name + " (&" + propName + ", &" + portp->name() + ");\n"); + name + " (&" + propName + ", &" + portp->name() + ");\n");
cfuncp->addStmtsp(new AstCStmt(portp->fileline(), varCode)); cfuncp->addStmtsp(new AstCStmt{portp->fileline(), varCode});
args += "&" + name; args += "&" + name;
} else { } else {
if (portp->isWritable() && portp->basicp()->isDpiPrimitive()) { if (portp->isWritable() && portp->basicp()->isDpiPrimitive()) {
@ -1029,7 +1029,7 @@ private:
// Store context, if needed // Store context, if needed
if (nodep->dpiContext()) { if (nodep->dpiContext()) {
const string stmt = "Verilated::dpiContext(__Vscopep, __Vfilenamep, __Vlineno);\n"; const string stmt = "Verilated::dpiContext(__Vscopep, __Vfilenamep, __Vlineno);\n";
cfuncp->addStmtsp(new AstCStmt(nodep->fileline(), stmt)); cfuncp->addStmtsp(new AstCStmt{nodep->fileline(), stmt});
} }
{ // Call the imported function { // Call the imported function
@ -1038,9 +1038,9 @@ private:
string stmt = rtnvscp->varp()->name(); string stmt = rtnvscp->varp()->name();
stmt += tmpSuffixp; stmt += tmpSuffixp;
stmt += rtnvscp->varp()->basicp()->isDpiPrimitive() ? " = " : "[0] = "; stmt += rtnvscp->varp()->basicp()->isDpiPrimitive() ? " = " : "[0] = ";
cfuncp->addStmtsp(new AstText(nodep->fileline(), stmt, /* tracking: */ true)); cfuncp->addStmtsp(new AstText{nodep->fileline(), stmt, /* tracking: */ true});
} }
AstCCall* const callp = new AstCCall(nodep->fileline(), dpiFuncp); AstCCall* const callp = new AstCCall{nodep->fileline(), dpiFuncp};
callp->dtypeSetVoid(); callp->dtypeSetVoid();
callp->argTypes(args); callp->argTypes(args);
cfuncp->addStmtsp(callp->makeStmt()); cfuncp->addStmtsp(callp->makeStmt());
@ -1139,7 +1139,7 @@ private:
AstVarScope* rtnvscp = nullptr; AstVarScope* rtnvscp = nullptr;
if (rtnvarp) { if (rtnvarp) {
rtnvscp = new AstVarScope(rtnvarp->fileline(), m_scopep, rtnvarp); rtnvscp = new AstVarScope{rtnvarp->fileline(), m_scopep, rtnvarp};
m_scopep->addVarsp(rtnvscp); m_scopep->addVarsp(rtnvscp);
rtnvarp->user2p(rtnvscp); rtnvarp->user2p(rtnvscp);
} }
@ -1157,9 +1157,9 @@ private:
string suffix; // So, make them unique string suffix; // So, make them unique
if (!nodep->taskPublic() && !nodep->classMethod()) suffix = "_" + m_scopep->nameDotless(); if (!nodep->taskPublic() && !nodep->classMethod()) suffix = "_" + m_scopep->nameDotless();
const string name = ((nodep->name() == "new") ? "new" : prefix + nodep->name() + suffix); const string name = ((nodep->name() == "new") ? "new" : prefix + nodep->name() + suffix);
AstCFunc* const cfuncp = new AstCFunc( AstCFunc* const cfuncp = new AstCFunc{
nodep->fileline(), name, m_scopep, nodep->fileline(), name, m_scopep,
((nodep->taskPublic() && rtnvarp) ? rtnvarp->cPubArgType(true, true) : "")); ((nodep->taskPublic() && rtnvarp) ? rtnvarp->cPubArgType(true, true) : "")};
// It's ok to combine imports because this is just a wrapper; // It's ok to combine imports because this is just a wrapper;
// duplicate wrappers can get merged. // duplicate wrappers can get merged.
cfuncp->dontCombine(!nodep->dpiImport()); cfuncp->dontCombine(!nodep->dpiImport());
@ -1192,7 +1192,7 @@ private:
cfuncp->argTypes(EmitCBaseVisitor::symClassVar()); cfuncp->argTypes(EmitCBaseVisitor::symClassVar());
if (cfuncp->name() == "new") { if (cfuncp->name() == "new") {
const string stmt = VIdProtect::protect("_ctor_var_reset") + "(vlSymsp);\n"; const string stmt = VIdProtect::protect("_ctor_var_reset") + "(vlSymsp);\n";
cfuncp->addInitsp(new AstCStmt(nodep->fileline(), stmt)); cfuncp->addInitsp(new AstCStmt{nodep->fileline(), stmt});
} }
} }
if (nodep->dpiContext()) { if (nodep->dpiContext()) {
@ -1267,8 +1267,8 @@ private:
// Return statement // Return statement
if (rtnvscp && nodep->taskPublic()) { if (rtnvscp && nodep->taskPublic()) {
cfuncp->addFinalsp(new AstCReturn( cfuncp->addFinalsp(new AstCReturn{
rtnvscp->fileline(), new AstVarRef(rtnvscp->fileline(), rtnvscp, VAccess::READ))); rtnvscp->fileline(), new AstVarRef{rtnvscp->fileline(), rtnvscp, VAccess::READ}});
} }
// Replace variable refs // Replace variable refs
relink(cfuncp); relink(cfuncp);
@ -1412,7 +1412,7 @@ private:
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
} else if (!VN_IS(nodep->backp(), StmtExpr)) { } else if (!VN_IS(nodep->backp(), StmtExpr)) {
UASSERT_OBJ(nodep->taskp()->isFunction(), nodep, "func reference to non-function"); UASSERT_OBJ(nodep->taskp()->isFunction(), nodep, "func reference to non-function");
AstVarRef* const outrefp = new AstVarRef(nodep->fileline(), outvscp, VAccess::READ); AstVarRef* const outrefp = new AstVarRef{nodep->fileline(), outvscp, VAccess::READ};
nodep->replaceWith(outrefp); nodep->replaceWith(outrefp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
} else { } else {
@ -1634,7 +1634,7 @@ V3TaskConnects V3Task::taskConnects(AstNodeFTaskRef* nodep, AstNode* taskStmtsp)
nodep->v3error("Missing argument on non-defaulted argument " nodep->v3error("Missing argument on non-defaulted argument "
<< portp->prettyNameQ() << " in function call to " << portp->prettyNameQ() << " in function call to "
<< nodep->taskp()->prettyTypeName()); << nodep->taskp()->prettyTypeName());
newvaluep = new AstConst(nodep->fileline(), AstConst::Unsized32(), 0); newvaluep = new AstConst{nodep->fileline(), AstConst::Unsized32{}, 0};
} else if (!VN_IS(portp->valuep(), Const)) { } else if (!VN_IS(portp->valuep(), Const)) {
// The default value for this port might be a constant // The default value for this port might be a constant
// expression that hasn't been folded yet. Try folding it // expression that hasn't been folded yet. Try folding it
@ -1648,7 +1648,7 @@ V3TaskConnects V3Task::taskConnects(AstNodeFTaskRef* nodep, AstNode* taskStmtsp)
"Unsupported: Non-constant default value in missing argument " "Unsupported: Non-constant default value in missing argument "
<< portp->prettyNameQ() << " in function call to " << portp->prettyNameQ() << " in function call to "
<< nodep->taskp()->prettyTypeName()); << nodep->taskp()->prettyTypeName());
newvaluep = new AstConst(nodep->fileline(), AstConst::Unsized32(), 0); newvaluep = new AstConst{nodep->fileline(), AstConst::Unsized32{}, 0};
} else { } else {
newvaluep = newvaluep->cloneTree(true); newvaluep = newvaluep->cloneTree(true);
} }
@ -1658,7 +1658,7 @@ V3TaskConnects V3Task::taskConnects(AstNodeFTaskRef* nodep, AstNode* taskStmtsp)
// To avoid problems with callee needing to know to deleteTree // To avoid problems with callee needing to know to deleteTree
// or not, we make this into a pin // or not, we make this into a pin
UINFO(9, "Default pin for " << portp << endl); UINFO(9, "Default pin for " << portp << endl);
AstArg* const newp = new AstArg(nodep->fileline(), portp->name(), newvaluep); AstArg* const newp = new AstArg{nodep->fileline(), portp->name(), newvaluep};
if (tconnects[i].second) { // Have a "nullptr" pin already defined for it if (tconnects[i].second) { // Have a "nullptr" pin already defined for it
VL_DO_CLEAR(tconnects[i].second->unlinkFrBack()->deleteTree(), VL_DO_CLEAR(tconnects[i].second->unlinkFrBack()->deleteTree(),
tconnects[i].second = nullptr); tconnects[i].second = nullptr);

View File

@ -413,7 +413,7 @@ private:
// equation is heuristic. // equation is heuristic.
if (complexity <= actSet.size() * 2) { if (complexity <= actSet.size() * 2) {
for (; head != it; ++head) { for (; head != it; ++head) {
new V3GraphEdge(&m_graph, m_alwaysVtxp, head->second, 1); new V3GraphEdge{&m_graph, m_alwaysVtxp, head->second, 1};
} }
} }
} }
@ -422,13 +422,13 @@ private:
} }
AstNodeExpr* selectActivity(FileLine* flp, uint32_t acode, const VAccess& access) { AstNodeExpr* selectActivity(FileLine* flp, uint32_t acode, const VAccess& access) {
return new AstArraySel(flp, new AstVarRef(flp, m_activityVscp, access), acode); return new AstArraySel(flp, new AstVarRef{flp, m_activityVscp, access}, acode);
} }
void addActivitySetter(AstNode* insertp, uint32_t code) { void addActivitySetter(AstNode* insertp, uint32_t code) {
FileLine* const fl = insertp->fileline(); FileLine* const fl = insertp->fileline();
AstAssign* const setterp = new AstAssign(fl, selectActivity(fl, code, VAccess::WRITE), AstAssign* const setterp = new AstAssign{fl, selectActivity(fl, code, VAccess::WRITE),
new AstConst(fl, AstConst::BitTrue())); new AstConst{fl, AstConst::BitTrue{}}};
if (AstStmtExpr* const stmtp = VN_CAST(insertp, StmtExpr)) { if (AstStmtExpr* const stmtp = VN_CAST(insertp, StmtExpr)) {
stmtp->addNextHere(setterp); stmtp->addNextHere(setterp);
} else if (AstCFunc* const funcp = VN_CAST(insertp, CFunc)) { } else if (AstCFunc* const funcp = VN_CAST(insertp, CFunc)) {
@ -459,12 +459,12 @@ private:
v3Global.rootp()->typeTablep()->addTypesp(newScalarDtp); v3Global.rootp()->typeTablep()->addTypesp(newScalarDtp);
AstRange* const newArange AstRange* const newArange
= new AstRange{flp, VNumRange{static_cast<int>(m_activityNumber) - 1, 0}}; = new AstRange{flp, VNumRange{static_cast<int>(m_activityNumber) - 1, 0}};
AstNodeDType* const newArrDtp = new AstUnpackArrayDType(flp, newScalarDtp, newArange); AstNodeDType* const newArrDtp = new AstUnpackArrayDType{flp, newScalarDtp, newArange};
v3Global.rootp()->typeTablep()->addTypesp(newArrDtp); v3Global.rootp()->typeTablep()->addTypesp(newArrDtp);
AstVar* const newvarp AstVar* const newvarp
= new AstVar(flp, VVarType::MODULETEMP, "__Vm_traceActivity", newArrDtp); = new AstVar{flp, VVarType::MODULETEMP, "__Vm_traceActivity", newArrDtp};
m_topModp->addStmtsp(newvarp); m_topModp->addStmtsp(newvarp);
AstVarScope* const newvscp = new AstVarScope(flp, m_topScopep, newvarp); AstVarScope* const newvscp = new AstVarScope{flp, m_topScopep, newvarp};
m_topScopep->addVarsp(newvscp); m_topScopep->addVarsp(newvscp);
m_activityVscp = newvscp; m_activityVscp = newvscp;
@ -495,7 +495,7 @@ private:
: "trace_chg_sub_"; : "trace_chg_sub_";
FileLine* const flp = m_topScopep->fileline(); FileLine* const flp = m_topScopep->fileline();
AstCFunc* const funcp = new AstCFunc(flp, baseName + cvtToStr(funcNump++), m_topScopep); AstCFunc* const funcp = new AstCFunc{flp, baseName + cvtToStr(funcNump++), m_topScopep};
funcp->isTrace(true); funcp->isTrace(true);
funcp->dontCombine(true); funcp->dontCombine(true);
funcp->isLoose(true); funcp->isLoose(true);
@ -504,7 +504,7 @@ private:
// Add it to top scope // Add it to top scope
m_topScopep->addBlocksp(funcp); m_topScopep->addBlocksp(funcp);
const auto addInitStr = [funcp, flp](const string& str) -> void { const auto addInitStr = [funcp, flp](const string& str) -> void {
funcp->addInitsp(new AstCStmt(flp, str)); funcp->addInitsp(new AstCStmt{flp, str});
}; };
if (isTopFunc) { if (isTopFunc) {
// Top functions // Top functions
@ -519,13 +519,13 @@ private:
} }
// Register function // Register function
if (full) { if (full) {
m_regFuncp->addStmtsp(new AstText(flp, "tracep->addFullCb(", true)); m_regFuncp->addStmtsp(new AstText{flp, "tracep->addFullCb(", true});
} else { } else {
m_regFuncp->addStmtsp(new AstText(flp, "tracep->addChgCb(", true)); m_regFuncp->addStmtsp(new AstText{flp, "tracep->addChgCb(", true});
} }
m_regFuncp->addStmtsp(new AstAddrOfCFunc(flp, funcp)); m_regFuncp->addStmtsp(new AstAddrOfCFunc{flp, funcp});
m_regFuncp->addStmtsp(new AstText(flp, ", vlSelf", true)); m_regFuncp->addStmtsp(new AstText{flp, ", vlSelf", true});
m_regFuncp->addStmtsp(new AstText(flp, ");\n", true)); m_regFuncp->addStmtsp(new AstText{flp, ");\n", true});
} else { } else {
// Sub functions // Sub functions
funcp->argTypes(v3Global.opt.traceClassBase() funcp->argTypes(v3Global.opt.traceClassBase()
@ -551,7 +551,7 @@ private:
} }
} }
// Add call to top function // Add call to top function
AstCCall* const callp = new AstCCall(funcp->fileline(), funcp); AstCCall* const callp = new AstCCall{funcp->fileline(), funcp};
callp->dtypeSetVoid(); callp->dtypeSetVoid();
callp->argTypes("bufp"); callp->argTypes("bufp");
topFuncp->addStmtsp(callp->makeStmt()); topFuncp->addStmtsp(callp->makeStmt());
@ -609,7 +609,7 @@ private:
// Add TraceInc node // Add TraceInc node
AstTraceInc* const incp AstTraceInc* const incp
= new AstTraceInc(declp->fileline(), declp, /* full: */ true); = new AstTraceInc{declp->fileline(), declp, /* full: */ true};
subFuncp->addStmtsp(incp); subFuncp->addStmtsp(incp);
subStmts += incp->nodeCount(); subStmts += incp->nodeCount();
@ -669,14 +669,14 @@ private:
const bool always = actSet.count(TraceActivityVertex::ACTIVITY_ALWAYS) != 0; const bool always = actSet.count(TraceActivityVertex::ACTIVITY_ALWAYS) != 0;
AstNodeExpr* condp = nullptr; AstNodeExpr* condp = nullptr;
if (always) { if (always) {
condp = new AstConst(flp, 1); // Always true, will be folded later condp = new AstConst{flp, 1}; // Always true, will be folded later
} else { } else {
for (const uint32_t actCode : actSet) { for (const uint32_t actCode : actSet) {
AstNodeExpr* const selp = selectActivity(flp, actCode, VAccess::READ); AstNodeExpr* const selp = selectActivity(flp, actCode, VAccess::READ);
condp = condp ? new AstOr(flp, condp, selp) : selp; condp = condp ? new AstOr{flp, condp, selp} : selp;
} }
} }
ifp = new AstIf(flp, condp); ifp = new AstIf{flp, condp};
if (!always) ifp->branchPred(VBranchPred::BP_UNLIKELY); if (!always) ifp->branchPred(VBranchPred::BP_UNLIKELY);
subFuncp->addStmtsp(ifp); subFuncp->addStmtsp(ifp);
subStmts += ifp->nodeCount(); subStmts += ifp->nodeCount();
@ -685,7 +685,7 @@ private:
// Add TraceInc node // Add TraceInc node
AstTraceInc* const incp AstTraceInc* const incp
= new AstTraceInc(declp->fileline(), declp, /* full: */ false, baseCode); = new AstTraceInc{declp->fileline(), declp, /* full: */ false, baseCode};
ifp->addThensp(incp); ifp->addThensp(incp);
subStmts += incp->nodeCount(); subStmts += incp->nodeCount();
@ -701,7 +701,7 @@ private:
void createCleanupFunction() { void createCleanupFunction() {
FileLine* const fl = m_topScopep->fileline(); FileLine* const fl = m_topScopep->fileline();
AstCFunc* const cleanupFuncp = new AstCFunc(fl, "trace_cleanup", m_topScopep); AstCFunc* const cleanupFuncp = new AstCFunc{fl, "trace_cleanup", m_topScopep};
cleanupFuncp->argTypes("void* voidSelf, " + v3Global.opt.traceClassBase() cleanupFuncp->argTypes("void* voidSelf, " + v3Global.opt.traceClassBase()
+ "* /*unused*/"); + "* /*unused*/");
cleanupFuncp->isTrace(true); cleanupFuncp->isTrace(true);
@ -709,22 +709,22 @@ private:
cleanupFuncp->isStatic(true); cleanupFuncp->isStatic(true);
cleanupFuncp->isLoose(true); cleanupFuncp->isLoose(true);
m_topScopep->addBlocksp(cleanupFuncp); m_topScopep->addBlocksp(cleanupFuncp);
cleanupFuncp->addInitsp(new AstCStmt(fl, voidSelfAssign(m_topModp))); cleanupFuncp->addInitsp(new AstCStmt{fl, voidSelfAssign(m_topModp)});
cleanupFuncp->addInitsp(new AstCStmt(fl, symClassAssign())); cleanupFuncp->addInitsp(new AstCStmt{fl, symClassAssign()});
// Register it // Register it
m_regFuncp->addStmtsp(new AstText(fl, "tracep->addCleanupCb(", true)); m_regFuncp->addStmtsp(new AstText{fl, "tracep->addCleanupCb(", true});
m_regFuncp->addStmtsp(new AstAddrOfCFunc(fl, cleanupFuncp)); m_regFuncp->addStmtsp(new AstAddrOfCFunc{fl, cleanupFuncp});
m_regFuncp->addStmtsp(new AstText(fl, ", vlSelf);\n", true)); m_regFuncp->addStmtsp(new AstText{fl, ", vlSelf);\n", true});
// Clear global activity flag // Clear global activity flag
cleanupFuncp->addStmtsp( cleanupFuncp->addStmtsp(new AstCStmt{m_topScopep->fileline(),
new AstCStmt(m_topScopep->fileline(), string("vlSymsp->__Vm_activity = false;\n"))); std::string{"vlSymsp->__Vm_activity = false;\n"}});
// Clear fine grained activity flags // Clear fine grained activity flags
for (uint32_t i = 0; i < m_activityNumber; ++i) { for (uint32_t i = 0; i < m_activityNumber; ++i) {
AstNode* const clrp = new AstAssign(fl, selectActivity(fl, i, VAccess::WRITE), AstNode* const clrp = new AstAssign{fl, selectActivity(fl, i, VAccess::WRITE),
new AstConst(fl, AstConst::BitFalse())); new AstConst{fl, AstConst::BitFalse{}}};
cleanupFuncp->addStmtsp(clrp); cleanupFuncp->addStmtsp(clrp);
} }
} }
@ -759,7 +759,7 @@ private:
// last value vector is more compact // last value vector is more compact
// Create the trace registration function // Create the trace registration function
m_regFuncp = new AstCFunc(m_topScopep->fileline(), "trace_register", m_topScopep); m_regFuncp = new AstCFunc{m_topScopep->fileline(), "trace_register", m_topScopep};
m_regFuncp->argTypes(v3Global.opt.traceClassBase() + "* tracep"); m_regFuncp->argTypes(v3Global.opt.traceClassBase() + "* tracep");
m_regFuncp->isTrace(true); m_regFuncp->isTrace(true);
m_regFuncp->slow(true); m_regFuncp->slow(true);
@ -789,7 +789,7 @@ private:
TraceCFuncVertex* vertexp TraceCFuncVertex* vertexp
= dynamic_cast<TraceCFuncVertex*>(nodep->user1u().toGraphVertex()); = dynamic_cast<TraceCFuncVertex*>(nodep->user1u().toGraphVertex());
if (!vertexp) { if (!vertexp) {
vertexp = new TraceCFuncVertex(&m_graph, nodep); vertexp = new TraceCFuncVertex{&m_graph, nodep};
nodep->user1p(vertexp); nodep->user1p(vertexp);
} }
return vertexp; return vertexp;
@ -798,7 +798,7 @@ private:
TraceActivityVertex* vertexp TraceActivityVertex* vertexp
= dynamic_cast<TraceActivityVertex*>(nodep->user3u().toGraphVertex()); = dynamic_cast<TraceActivityVertex*>(nodep->user3u().toGraphVertex());
if (!vertexp) { if (!vertexp) {
vertexp = new TraceActivityVertex(&m_graph, nodep, slow); vertexp = new TraceActivityVertex{&m_graph, nodep, slow};
nodep->user3p(vertexp); nodep->user3p(vertexp);
} }
vertexp->slow(slow); vertexp->slow(slow);
@ -840,7 +840,7 @@ private:
UINFO(8, " SubCCALL " << ccallp << endl); UINFO(8, " SubCCALL " << ccallp << endl);
V3GraphVertex* const ccallFuncVtxp = getCFuncVertexp(ccallp->funcp()); V3GraphVertex* const ccallFuncVtxp = getCFuncVertexp(ccallp->funcp());
activityVtxp->slow(ccallp->funcp()->slow()); activityVtxp->slow(ccallp->funcp()->slow());
new V3GraphEdge(&m_graph, activityVtxp, ccallFuncVtxp, 1); new V3GraphEdge{&m_graph, activityVtxp, ccallFuncVtxp, 1};
} }
} }
} }
@ -858,7 +858,7 @@ private:
// Cannot treat a coroutine as slow, it may be resumed later // Cannot treat a coroutine as slow, it may be resumed later
const bool slow = nodep->slow() && !nodep->isCoroutine(); const bool slow = nodep->slow() && !nodep->isCoroutine();
V3GraphVertex* const activityVtxp = getActivityVertexp(nodep, slow); V3GraphVertex* const activityVtxp = getActivityVertexp(nodep, slow);
new V3GraphEdge(&m_graph, activityVtxp, funcVtxp, 1); new V3GraphEdge{&m_graph, activityVtxp, funcVtxp, 1};
} }
} }
VL_RESTORER(m_cfuncp); VL_RESTORER(m_cfuncp);
@ -870,7 +870,7 @@ private:
void visit(AstTraceDecl* nodep) override { void visit(AstTraceDecl* nodep) override {
UINFO(8, " TRACE " << nodep << endl); UINFO(8, " TRACE " << nodep << endl);
if (!m_finding) { if (!m_finding) {
V3GraphVertex* const vertexp = new TraceTraceVertex(&m_graph, nodep); V3GraphVertex* const vertexp = new TraceTraceVertex{&m_graph, nodep};
nodep->user1p(vertexp); nodep->user1p(vertexp);
UASSERT_OBJ(m_cfuncp, nodep, "Trace not under func"); UASSERT_OBJ(m_cfuncp, nodep, "Trace not under func");
@ -885,21 +885,21 @@ private:
UASSERT_OBJ(nodep->access().isReadOnly(), nodep, "Lvalue in trace? Should be const."); UASSERT_OBJ(nodep->access().isReadOnly(), nodep, "Lvalue in trace? Should be const.");
V3GraphVertex* varVtxp = nodep->varScopep()->user1u().toGraphVertex(); V3GraphVertex* varVtxp = nodep->varScopep()->user1u().toGraphVertex();
if (!varVtxp) { if (!varVtxp) {
varVtxp = new TraceVarVertex(&m_graph, nodep->varScopep()); varVtxp = new TraceVarVertex{&m_graph, nodep->varScopep()};
nodep->varScopep()->user1p(varVtxp); nodep->varScopep()->user1p(varVtxp);
} }
V3GraphVertex* const traceVtxp = m_tracep->user1u().toGraphVertex(); V3GraphVertex* const traceVtxp = m_tracep->user1u().toGraphVertex();
new V3GraphEdge(&m_graph, varVtxp, traceVtxp, 1); new V3GraphEdge{&m_graph, varVtxp, traceVtxp, 1};
if (nodep->varp()->isPrimaryInish() // Always need to trace primary inputs if (nodep->varp()->isPrimaryInish() // Always need to trace primary inputs
|| nodep->varp()->isSigPublic()) { // Or ones user can change || nodep->varp()->isSigPublic()) { // Or ones user can change
new V3GraphEdge(&m_graph, m_alwaysVtxp, traceVtxp, 1); new V3GraphEdge{&m_graph, m_alwaysVtxp, traceVtxp, 1};
} }
} else if (m_cfuncp && m_finding && nodep->access().isWriteOrRW()) { } else if (m_cfuncp && m_finding && nodep->access().isWriteOrRW()) {
UASSERT_OBJ(nodep->varScopep(), nodep, "No var scope?"); UASSERT_OBJ(nodep->varScopep(), nodep, "No var scope?");
V3GraphVertex* const funcVtxp = getCFuncVertexp(m_cfuncp); V3GraphVertex* const funcVtxp = getCFuncVertexp(m_cfuncp);
V3GraphVertex* const varVtxp = nodep->varScopep()->user1u().toGraphVertex(); V3GraphVertex* const varVtxp = nodep->varScopep()->user1u().toGraphVertex();
if (varVtxp) { // else we're not tracing this signal if (varVtxp) { // else we're not tracing this signal
new V3GraphEdge(&m_graph, funcVtxp, varVtxp, 1); new V3GraphEdge{&m_graph, funcVtxp, varVtxp, 1};
} }
} }
} }

View File

@ -205,7 +205,7 @@ private:
TristateVertex* vertexp = reinterpret_cast<TristateVertex*>(nodep->user5p()); TristateVertex* vertexp = reinterpret_cast<TristateVertex*>(nodep->user5p());
if (!vertexp) { if (!vertexp) {
UINFO(6, " New vertex " << nodep << endl); UINFO(6, " New vertex " << nodep << endl);
vertexp = new TristateVertex(&m_graph, nodep); vertexp = new TristateVertex{&m_graph, nodep};
nodep->user5p(vertexp); nodep->user5p(vertexp);
} }
return vertexp; return vertexp;
@ -297,7 +297,7 @@ public:
if (dumpGraph() >= 9) m_graph.dumpDotFilePrefixed("tri_pos__" + nodep->name()); if (dumpGraph() >= 9) m_graph.dumpDotFilePrefixed("tri_pos__" + nodep->name());
} }
void associate(AstNode* fromp, AstNode* top) { void associate(AstNode* fromp, AstNode* top) {
new V3GraphEdge(&m_graph, makeVertex(fromp), makeVertex(top), 1); new V3GraphEdge{&m_graph, makeVertex(fromp), makeVertex(top), 1};
} }
void deleteVerticesFromSubtreeRecurse(AstNode* nodep) { void deleteVerticesFromSubtreeRecurse(AstNode* nodep) {
if (!nodep) return; if (!nodep) return;
@ -485,8 +485,8 @@ class TristateVisitor final : public TristateBaseVisitor {
AstVar* getCreateEnVarp(AstVar* invarp) { AstVar* getCreateEnVarp(AstVar* invarp) {
// Return the master __en for the specified input variable // Return the master __en for the specified input variable
if (!invarp->user1p()) { if (!invarp->user1p()) {
AstVar* const newp = new AstVar(invarp->fileline(), VVarType::MODULETEMP, AstVar* const newp = new AstVar{invarp->fileline(), VVarType::MODULETEMP,
invarp->name() + "__en", invarp); invarp->name() + "__en", invarp};
UINFO(9, " newenv " << newp << endl); UINFO(9, " newenv " << newp << endl);
modAddStmtp(invarp, newp); modAddStmtp(invarp, newp);
invarp->user1p(newp); // find envar given invarp invarp->user1p(newp); // find envar given invarp
@ -537,8 +537,8 @@ class TristateVisitor final : public TristateBaseVisitor {
AstVar* getCreateOutVarp(AstVar* invarp) { AstVar* getCreateOutVarp(AstVar* invarp) {
// Return the master __out for the specified input variable // Return the master __out for the specified input variable
if (!invarp->user4p()) { if (!invarp->user4p()) {
AstVar* const newp = new AstVar(invarp->fileline(), VVarType::MODULETEMP, AstVar* const newp = new AstVar{invarp->fileline(), VVarType::MODULETEMP,
invarp->name() + "__out", invarp); invarp->name() + "__out", invarp};
UINFO(9, " newout " << newp << endl); UINFO(9, " newout " << newp << endl);
modAddStmtp(invarp, newp); modAddStmtp(invarp, newp);
invarp->user4p(newp); // find outvar given invarp invarp->user4p(newp); // find outvar given invarp
@ -546,8 +546,8 @@ class TristateVisitor final : public TristateBaseVisitor {
return VN_AS(invarp->user4p(), Var); return VN_AS(invarp->user4p(), Var);
} }
AstVar* getCreateUnconnVarp(AstNode* fromp, AstNodeDType* dtypep) { AstVar* getCreateUnconnVarp(AstNode* fromp, AstNodeDType* dtypep) {
AstVar* const newp = new AstVar(fromp->fileline(), VVarType::MODULETEMP, AstVar* const newp = new AstVar{fromp->fileline(), VVarType::MODULETEMP,
"__Vtriunconn" + cvtToStr(m_unique++), dtypep); "__Vtriunconn" + cvtToStr(m_unique++), dtypep};
UINFO(9, " newunc " << newp << endl); UINFO(9, " newunc " << newp << endl);
modAddStmtp(newp, newp); modAddStmtp(newp, newp);
return newp; return newp;
@ -569,9 +569,9 @@ class TristateVisitor final : public TristateBaseVisitor {
AstNodeExpr* newEnableDeposit(AstSel* selp, AstNodeExpr* enp) { AstNodeExpr* newEnableDeposit(AstSel* selp, AstNodeExpr* enp) {
// Form a "deposit" instruction for given enable, using existing select as a template. // Form a "deposit" instruction for given enable, using existing select as a template.
// Would be nicer if we made this a new AST type // Would be nicer if we made this a new AST type
AstNodeExpr* const newp = new AstShiftL( AstNodeExpr* const newp = new AstShiftL{
selp->fileline(), new AstExtend(selp->fileline(), enp, selp->fromp()->width()), selp->fileline(), new AstExtend{selp->fileline(), enp, selp->fromp()->width()},
selp->lsbp()->cloneTree(false), selp->fromp()->width()); selp->lsbp()->cloneTree(false), selp->fromp()->width()};
return newp; return newp;
} }
@ -622,8 +622,8 @@ class TristateVisitor final : public TristateBaseVisitor {
UINFO(8, " Adding driver to var " << varp << endl); UINFO(8, " Adding driver to var " << varp << endl);
AstConst* const constp = newAllZerosOrOnes(varp, false); AstConst* const constp = newAllZerosOrOnes(varp, false);
AstVarRef* const varrefp AstVarRef* const varrefp
= new AstVarRef(varp->fileline(), varp, VAccess::WRITE); = new AstVarRef{varp->fileline(), varp, VAccess::WRITE};
AstNode* const newp = new AstAssignW(varp->fileline(), varrefp, constp); AstNode* const newp = new AstAssignW{varp->fileline(), varrefp, constp};
UINFO(9, " newoev " << newp << endl); UINFO(9, " newoev " << newp << endl);
varrefp->user1p(newAllZerosOrOnes(varp, false)); varrefp->user1p(newAllZerosOrOnes(varp, false));
nodep->addStmtsp(newp); nodep->addStmtsp(newp);
@ -993,7 +993,7 @@ class TristateVisitor final : public TristateBaseVisitor {
// due to the pinReconnectSimple call in visit AstPin. // due to the pinReconnectSimple call in visit AstPin.
// We can ignore the output override by making a temporary // We can ignore the output override by making a temporary
AstVar* const varp = getCreateUnconnVarp(nodep, nodep->dtypep()); AstVar* const varp = getCreateUnconnVarp(nodep, nodep->dtypep());
AstNode* const newp = new AstVarRef(nodep->fileline(), varp, VAccess::WRITE); AstNode* const newp = new AstVarRef{nodep->fileline(), varp, VAccess::WRITE};
UINFO(9, " const->" << newp << endl); UINFO(9, " const->" << newp << endl);
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(pushDeletep(nodep), nodep); VL_DO_DANGLING(pushDeletep(nodep), nodep);
@ -1047,7 +1047,7 @@ class TristateVisitor final : public TristateBaseVisitor {
// The output enable of a cond is a cond of the output enable of the // The output enable of a cond is a cond of the output enable of the
// two expressions with the same conditional. // two expressions with the same conditional.
AstNodeExpr* const enp AstNodeExpr* const enp
= new AstCond(nodep->fileline(), condp->cloneTree(false), en1p, en2p); = new AstCond{nodep->fileline(), condp->cloneTree(false), en1p, en2p};
UINFO(9, " newcond " << enp << endl); UINFO(9, " newcond " << enp << endl);
nodep->user1p(enp); // propagate up COND(lhsp->enable, rhsp->enable) nodep->user1p(enp); // propagate up COND(lhsp->enable, rhsp->enable)
thenp->user1p(nullptr); thenp->user1p(nullptr);
@ -1086,8 +1086,8 @@ class TristateVisitor final : public TristateBaseVisitor {
if (nodep->fromp()->user1p()) { // SEL(VARREF, lsb) if (nodep->fromp()->user1p()) { // SEL(VARREF, lsb)
AstNodeExpr* const en1p = getEnp(nodep->fromp()); AstNodeExpr* const en1p = getEnp(nodep->fromp());
AstNodeExpr* const enp AstNodeExpr* const enp
= new AstSel(nodep->fileline(), en1p, nodep->lsbp()->cloneTree(true), = new AstSel{nodep->fileline(), en1p, nodep->lsbp()->cloneTree(true),
nodep->widthp()->cloneTree(true)); nodep->widthp()->cloneTree(true)};
UINFO(9, " newsel " << enp << endl); UINFO(9, " newsel " << enp << endl);
nodep->user1p(enp); // propagate up SEL(fromp->enable, value) nodep->user1p(enp); // propagate up SEL(fromp->enable, value)
m_tgraph.didProcess(nodep); m_tgraph.didProcess(nodep);
@ -1113,11 +1113,11 @@ class TristateVisitor final : public TristateBaseVisitor {
// Each half of the concat gets a select of the enable expression // Each half of the concat gets a select of the enable expression
AstNodeExpr* const enp = VN_AS(nodep->user1p(), NodeExpr); AstNodeExpr* const enp = VN_AS(nodep->user1p(), NodeExpr);
nodep->user1p(nullptr); nodep->user1p(nullptr);
nodep->lhsp()->user1p(new AstSel(nodep->fileline(), enp->cloneTree(true), nodep->lhsp()->user1p(new AstSel{nodep->fileline(), enp->cloneTree(true),
nodep->rhsp()->width(), nodep->rhsp()->width(),
nodep->lhsp()->width())); nodep->lhsp()->width()});
nodep->rhsp()->user1p( nodep->rhsp()->user1p(
new AstSel(nodep->fileline(), enp, 0, nodep->rhsp()->width())); new AstSel{nodep->fileline(), enp, 0, nodep->rhsp()->width()});
m_tgraph.didProcess(nodep); m_tgraph.didProcess(nodep);
} }
iterateChildren(nodep); iterateChildren(nodep);
@ -1132,7 +1132,7 @@ class TristateVisitor final : public TristateBaseVisitor {
m_tgraph.didProcess(nodep); m_tgraph.didProcess(nodep);
AstNodeExpr* const en1p = getEnp(expr1p); AstNodeExpr* const en1p = getEnp(expr1p);
AstNodeExpr* const en2p = getEnp(expr2p); AstNodeExpr* const en2p = getEnp(expr2p);
AstNodeExpr* const enp = new AstConcat(nodep->fileline(), en1p, en2p); AstNodeExpr* const enp = new AstConcat{nodep->fileline(), en1p, en2p};
UINFO(9, " newconc " << enp << endl); UINFO(9, " newconc " << enp << endl);
nodep->user1p(enp); // propagate up CONCAT(lhsp->enable, rhsp->enable) nodep->user1p(enp); // propagate up CONCAT(lhsp->enable, rhsp->enable)
expr1p->user1p(nullptr); expr1p->user1p(nullptr);
@ -1161,7 +1161,7 @@ class TristateVisitor final : public TristateBaseVisitor {
AstNodeExpr* const expr2p = nodep->rhsp()->unlinkFrBack(); AstNodeExpr* const expr2p = nodep->rhsp()->unlinkFrBack();
AstNodeExpr* enp; AstNodeExpr* enp;
if (AstNodeExpr* const en2p = VN_AS(expr2p->user1p(), NodeExpr)) { if (AstNodeExpr* const en2p = VN_AS(expr2p->user1p(), NodeExpr)) {
enp = new AstAnd(nodep->fileline(), expr1p, en2p); enp = new AstAnd{nodep->fileline(), expr1p, en2p};
} else { } else {
enp = expr1p; enp = expr1p;
} }
@ -1211,15 +1211,15 @@ class TristateVisitor final : public TristateBaseVisitor {
AstNodeExpr* subexpr1p = expr1p->cloneTree(false); AstNodeExpr* subexpr1p = expr1p->cloneTree(false);
AstNodeExpr* subexpr2p = expr2p->cloneTree(false); AstNodeExpr* subexpr2p = expr2p->cloneTree(false);
if (isAnd) { if (isAnd) {
subexpr1p = new AstNot(nodep->fileline(), subexpr1p); subexpr1p = new AstNot{nodep->fileline(), subexpr1p};
subexpr2p = new AstNot(nodep->fileline(), subexpr2p); subexpr2p = new AstNot{nodep->fileline(), subexpr2p};
} }
// calc new output enable // calc new output enable
AstNodeExpr* const enp = new AstOr( AstNodeExpr* const enp = new AstOr{
nodep->fileline(), new AstAnd(nodep->fileline(), en1p, en2p), nodep->fileline(), new AstAnd{nodep->fileline(), en1p, en2p},
new AstOr(nodep->fileline(), new AstOr{nodep->fileline(),
new AstAnd(nodep->fileline(), en1p->cloneTree(false), subexpr1p), new AstAnd{nodep->fileline(), en1p->cloneTree(false), subexpr1p},
new AstAnd(nodep->fileline(), en2p->cloneTree(false), subexpr2p))); new AstAnd{nodep->fileline(), en2p->cloneTree(false), subexpr2p}}};
UINFO(9, " neweqn " << enp << endl); UINFO(9, " neweqn " << enp << endl);
nodep->user1p(enp); nodep->user1p(enp);
expr1p->user1p(nullptr); expr1p->user1p(nullptr);
@ -1402,8 +1402,8 @@ class TristateVisitor final : public TristateBaseVisitor {
UINFO(4, " COUNTBITS('z)-> " << nodep << endl); UINFO(4, " COUNTBITS('z)-> " << nodep << endl);
VNRelinker relinkHandle; VNRelinker relinkHandle;
nodep->unlinkFrBack(&relinkHandle); nodep->unlinkFrBack(&relinkHandle);
AstNodeExpr* newp = new AstCountOnes( AstNodeExpr* newp = new AstCountOnes{
nodep->fileline(), new AstVarRef(nodep->fileline(), envarp, VAccess::READ)); nodep->fileline(), new AstVarRef{nodep->fileline(), envarp, VAccess::READ}};
if (nonXp) { // Need to still count '0 or '1 or 'x's if (nonXp) { // Need to still count '0 or '1 or 'x's
if (dropop[0]) { if (dropop[0]) {
nodep->rhsp()->unlinkFrBack()->deleteTree(); nodep->rhsp()->unlinkFrBack()->deleteTree();
@ -1417,7 +1417,7 @@ class TristateVisitor final : public TristateBaseVisitor {
nodep->fhsp()->unlinkFrBack()->deleteTree(); nodep->fhsp()->unlinkFrBack()->deleteTree();
nodep->fhsp(nonXp->cloneTree(true)); nodep->fhsp(nonXp->cloneTree(true));
} }
newp = new AstAdd(nodep->fileline(), nodep, newp); newp = new AstAdd{nodep->fileline(), nodep, newp};
} }
if (debug() >= 9) newp->dumpTree(cout, "-countout: "); if (debug() >= 9) newp->dumpTree(cout, "-countout: ");
relinkHandle.relink(newp); relinkHandle.relink(newp);
@ -1527,11 +1527,11 @@ class TristateVisitor final : public TristateBaseVisitor {
if (!nodep->exprp()) { // No-connect; covert to empty connection if (!nodep->exprp()) { // No-connect; covert to empty connection
UINFO(5, "Unconnected pin terminate " << nodep << endl); UINFO(5, "Unconnected pin terminate " << nodep << endl);
AstVar* const ucVarp = getCreateUnconnVarp(nodep, nodep->modVarp()->dtypep()); AstVar* const ucVarp = getCreateUnconnVarp(nodep, nodep->modVarp()->dtypep());
nodep->exprp(new AstVarRef(nodep->fileline(), ucVarp, nodep->exprp(new AstVarRef{nodep->fileline(), ucVarp,
// We converted, so use declaration output state // We converted, so use declaration output state
nodep->modVarp()->declDirection().isWritable() nodep->modVarp()->declDirection().isWritable()
? VAccess::WRITE ? VAccess::WRITE
: VAccess::READ)); : VAccess::READ});
m_tgraph.setTristate(ucVarp); m_tgraph.setTristate(ucVarp);
// We don't need a driver on the wire; the lack of one will default to tristate // We don't need a driver on the wire; the lack of one will default to tristate
} else if (inDeclProcessing) { // Not an input that was a converted tristate } else if (inDeclProcessing) { // Not an input that was a converted tristate
@ -1549,9 +1549,9 @@ class TristateVisitor final : public TristateBaseVisitor {
// Create the output enable pin, connect to new signal // Create the output enable pin, connect to new signal
AstNodeExpr* enrefp; AstNodeExpr* enrefp;
{ {
AstVar* const enVarp = new AstVar(nodep->fileline(), VVarType::MODULETEMP, AstVar* const enVarp = new AstVar{nodep->fileline(), VVarType::MODULETEMP,
nodep->name() + "__en" + cvtToStr(m_unique++), nodep->name() + "__en" + cvtToStr(m_unique++),
VFlagBitPacked(), enModVarp->width()); VFlagBitPacked{}, enModVarp->width()};
if (inDeclProcessing) { // __en(from-resolver-const) or __en(from-resolver-wire) if (inDeclProcessing) { // __en(from-resolver-const) or __en(from-resolver-wire)
enModVarp->varType2In(); enModVarp->varType2In();
} else { } else {
@ -1559,15 +1559,15 @@ class TristateVisitor final : public TristateBaseVisitor {
} }
UINFO(9, " newenv " << enVarp << endl); UINFO(9, " newenv " << enVarp << endl);
AstPin* const enpinp AstPin* const enpinp
= new AstPin(nodep->fileline(), nodep->pinNum(), = new AstPin{nodep->fileline(), nodep->pinNum(),
enModVarp->name(), // should be {var}"__en" enModVarp->name(), // should be {var}"__en"
new AstVarRef(nodep->fileline(), enVarp, VAccess::WRITE)); new AstVarRef{nodep->fileline(), enVarp, VAccess::WRITE}};
enpinp->modVarp(enModVarp); enpinp->modVarp(enModVarp);
UINFO(9, " newpin " << enpinp << endl); UINFO(9, " newpin " << enpinp << endl);
enpinp->user2(U2_BOTH); // don't iterate the pin later enpinp->user2(U2_BOTH); // don't iterate the pin later
nodep->addNextHere(enpinp); nodep->addNextHere(enpinp);
m_modp->addStmtsp(enVarp); m_modp->addStmtsp(enVarp);
enrefp = new AstVarRef(nodep->fileline(), enVarp, VAccess::READ); enrefp = new AstVarRef{nodep->fileline(), enVarp, VAccess::READ};
UINFO(9, " newvrf " << enrefp << endl); UINFO(9, " newvrf " << enrefp << endl);
if (debug() >= 9) enpinp->dumpTree(cout, "-pin-ena: "); if (debug() >= 9) enpinp->dumpTree(cout, "-pin-ena: ");
} }
@ -1584,9 +1584,9 @@ class TristateVisitor final : public TristateBaseVisitor {
} else { } else {
AstNodeExpr* const outexprp AstNodeExpr* const outexprp
= VN_AS(nodep->exprp(), NodeExpr)->cloneTree(false); // Note has lvalue() set = VN_AS(nodep->exprp(), NodeExpr)->cloneTree(false); // Note has lvalue() set
outpinp = new AstPin(nodep->fileline(), nodep->pinNum(), outpinp = new AstPin{nodep->fileline(), nodep->pinNum(),
outModVarp->name(), // should be {var}"__out" outModVarp->name(), // should be {var}"__out"
outexprp); outexprp};
outpinp->modVarp(outModVarp); outpinp->modVarp(outModVarp);
UINFO(9, " newpin " << outpinp << endl); UINFO(9, " newpin " << outpinp << endl);
outpinp->user2(U2_BOTH); // don't iterate the pin later outpinp->user2(U2_BOTH); // don't iterate the pin later
@ -1695,7 +1695,7 @@ class TristateVisitor final : public TristateBaseVisitor {
// Then propagate the enable from the original variable // Then propagate the enable from the original variable
UINFO(9, " Ref-to-tri " << nodep << endl); UINFO(9, " Ref-to-tri " << nodep << endl);
AstVar* const enVarp = getCreateEnVarp(nodep->varp()); AstVar* const enVarp = getCreateEnVarp(nodep->varp());
nodep->user1p(new AstVarRef(nodep->fileline(), enVarp, VAccess::READ)); nodep->user1p(new AstVarRef{nodep->fileline(), enVarp, VAccess::READ});
} }
if (m_alhs) {} // NOP; user1() already passed down from assignment if (m_alhs) {} // NOP; user1() already passed down from assignment
} }
@ -1709,9 +1709,9 @@ class TristateVisitor final : public TristateBaseVisitor {
if (nodep->user2() & U2_GRAPHING) return; // Already processed if (nodep->user2() & U2_GRAPHING) return; // Already processed
nodep->user2(U2_GRAPHING); nodep->user2(U2_GRAPHING);
if (nodep->isPulldown() || nodep->isPullup()) { if (nodep->isPulldown() || nodep->isPullup()) {
AstNode* const newp = new AstPull( AstNode* const newp = new AstPull{
nodep->fileline(), new AstVarRef(nodep->fileline(), nodep, VAccess::WRITE), nodep->fileline(), new AstVarRef{nodep->fileline(), nodep, VAccess::WRITE},
nodep->isPullup()); nodep->isPullup()};
UINFO(9, " newpul " << newp << endl); UINFO(9, " newpul " << newp << endl);
nodep->addNextHere(newp); nodep->addNextHere(newp);
// We'll iterate on the new AstPull later // We'll iterate on the new AstPull later

View File

@ -95,9 +95,9 @@ private:
if (m_assigndlyp) { if (m_assigndlyp) {
// Delayed assignments become normal assignments, // Delayed assignments become normal assignments,
// then the temp created becomes the delayed assignment // then the temp created becomes the delayed assignment
AstNode* const newp = new AstAssign(m_assigndlyp->fileline(), AstNode* const newp = new AstAssign{m_assigndlyp->fileline(),
m_assigndlyp->lhsp()->unlinkFrBackWithNext(), m_assigndlyp->lhsp()->unlinkFrBackWithNext(),
m_assigndlyp->rhsp()->unlinkFrBackWithNext()); m_assigndlyp->rhsp()->unlinkFrBackWithNext()};
m_assigndlyp->replaceWith(newp); m_assigndlyp->replaceWith(newp);
VL_DO_CLEAR(pushDeletep(m_assigndlyp), m_assigndlyp = nullptr); VL_DO_CLEAR(pushDeletep(m_assigndlyp), m_assigndlyp = nullptr);
} }
@ -116,23 +116,23 @@ private:
UASSERT_OBJ(!needDly, prep, "Should have already converted to non-delay"); UASSERT_OBJ(!needDly, prep, "Should have already converted to non-delay");
VNRelinker replaceHandle; VNRelinker replaceHandle;
AstNodeExpr* const earliercondp = ifp->condp()->unlinkFrBack(&replaceHandle); AstNodeExpr* const earliercondp = ifp->condp()->unlinkFrBack(&replaceHandle);
AstNodeExpr* const newp = new AstLogAnd(condp->fileline(), condp, earliercondp); AstNodeExpr* const newp = new AstLogAnd{condp->fileline(), condp, earliercondp};
UINFO(4, "Edit BOUNDLVALUE " << newp << endl); UINFO(4, "Edit BOUNDLVALUE " << newp << endl);
replaceHandle.relink(newp); replaceHandle.relink(newp);
} else { } else {
AstVar* const varp AstVar* const varp
= new AstVar(fl, VVarType::MODULETEMP, m_lvboundNames.get(prep), prep->dtypep()); = new AstVar{fl, VVarType::MODULETEMP, m_lvboundNames.get(prep), prep->dtypep()};
m_modp->addStmtsp(varp); m_modp->addStmtsp(varp);
AstNode* const abovep = prep->backp(); // Grab above point before we replace 'prep' AstNode* const abovep = prep->backp(); // Grab above point before we replace 'prep'
prep->replaceWith(new AstVarRef(fl, varp, VAccess::WRITE)); prep->replaceWith(new AstVarRef{fl, varp, VAccess::WRITE});
if (m_timingControlp) m_timingControlp->unlinkFrBack(); if (m_timingControlp) m_timingControlp->unlinkFrBack();
AstIf* const newp = new AstIf( AstIf* const newp = new AstIf{
fl, condp, fl, condp,
(needDly (needDly
? static_cast<AstNode*>(new AstAssignDly{ ? static_cast<AstNode*>(new AstAssignDly{
fl, prep, new AstVarRef{fl, varp, VAccess::READ}, m_timingControlp}) fl, prep, new AstVarRef{fl, varp, VAccess::READ}, m_timingControlp})
: static_cast<AstNode*>(new AstAssign{ : static_cast<AstNode*>(new AstAssign{
fl, prep, new AstVarRef{fl, varp, VAccess::READ}, m_timingControlp}))); fl, prep, new AstVarRef{fl, varp, VAccess::READ}, m_timingControlp}))};
newp->branchPred(VBranchPred::BP_LIKELY); newp->branchPred(VBranchPred::BP_LIKELY);
newp->isBoundsCheck(true); newp->isBoundsCheck(true);
if (debug() >= 9) newp->dumpTree(cout, " _new: "); if (debug() >= 9) newp->dumpTree(cout, " _new: ");
@ -213,15 +213,15 @@ private:
// If we got ==1'bx it can never be true (but 1'bx==1'bx can be!) // If we got ==1'bx it can never be true (but 1'bx==1'bx can be!)
if (((VN_IS(lhsp, Const) && VN_AS(lhsp, Const)->num().isFourState()) if (((VN_IS(lhsp, Const) && VN_AS(lhsp, Const)->num().isFourState())
|| (VN_IS(rhsp, Const) && VN_AS(rhsp, Const)->num().isFourState()))) { || (VN_IS(rhsp, Const) && VN_AS(rhsp, Const)->num().isFourState()))) {
newp = new AstConst(nodep->fileline(), AstConst::WidthedValue(), 1, newp = new AstConst(nodep->fileline(), AstConst::WidthedValue{}, 1,
(VN_IS(nodep, EqCase) ? 0 : 1)); (VN_IS(nodep, EqCase) ? 0 : 1));
VL_DO_DANGLING(lhsp->deleteTree(), lhsp); VL_DO_DANGLING(lhsp->deleteTree(), lhsp);
VL_DO_DANGLING(rhsp->deleteTree(), rhsp); VL_DO_DANGLING(rhsp->deleteTree(), rhsp);
} else { } else {
if (VN_IS(nodep, EqCase)) { if (VN_IS(nodep, EqCase)) {
newp = new AstEq(nodep->fileline(), lhsp, rhsp); newp = new AstEq{nodep->fileline(), lhsp, rhsp};
} else { } else {
newp = new AstNeq(nodep->fileline(), lhsp, rhsp); newp = new AstNeq{nodep->fileline(), lhsp, rhsp};
} }
} }
nodep->replaceWith(newp); nodep->replaceWith(newp);
@ -246,20 +246,20 @@ private:
nodep->v3warn(E_UNSUPPORTED, "Unsupported: RHS of ==? or !=? must be " nodep->v3warn(E_UNSUPPORTED, "Unsupported: RHS of ==? or !=? must be "
"constant to be synthesizable"); // Says spec. "constant to be synthesizable"); // Says spec.
// Replace with anything that won't cause more errors // Replace with anything that won't cause more errors
newp = new AstEq(nodep->fileline(), lhsp, rhsp); newp = new AstEq{nodep->fileline(), lhsp, rhsp};
} else { } else {
// X or Z's become mask, ala case statements. // X or Z's become mask, ala case statements.
V3Number nummask(rhsp, rhsp->width()); V3Number nummask{rhsp, rhsp->width()};
nummask.opBitsNonX(VN_AS(rhsp, Const)->num()); nummask.opBitsNonX(VN_AS(rhsp, Const)->num());
V3Number numval(rhsp, rhsp->width()); V3Number numval{rhsp, rhsp->width()};
numval.opBitsOne(VN_AS(rhsp, Const)->num()); numval.opBitsOne(VN_AS(rhsp, Const)->num());
AstNodeExpr* const and1p = new AstAnd(nodep->fileline(), lhsp, AstNodeExpr* const and1p = new AstAnd{nodep->fileline(), lhsp,
new AstConst(nodep->fileline(), nummask)); new AstConst{nodep->fileline(), nummask}};
AstNodeExpr* const and2p = new AstConst(nodep->fileline(), numval); AstNodeExpr* const and2p = new AstConst{nodep->fileline(), numval};
if (VN_IS(nodep, EqWild)) { if (VN_IS(nodep, EqWild)) {
newp = new AstEq(nodep->fileline(), and1p, and2p); newp = new AstEq{nodep->fileline(), and1p, and2p};
} else { } else {
newp = new AstNeq(nodep->fileline(), and1p, and2p); newp = new AstNeq{nodep->fileline(), and1p, and2p};
} }
VL_DO_DANGLING(rhsp->deleteTree(), rhsp); VL_DO_DANGLING(rhsp->deleteTree(), rhsp);
} }
@ -278,7 +278,7 @@ private:
iterateChildren(nodep); iterateChildren(nodep);
// Ahh, we're two state, so this is easy // Ahh, we're two state, so this is easy
UINFO(4, " ISUNKNOWN->0 " << nodep << endl); UINFO(4, " ISUNKNOWN->0 " << nodep << endl);
AstConst* const newp = new AstConst(nodep->fileline(), AstConst::BitFalse()); AstConst* const newp = new AstConst{nodep->fileline(), AstConst::BitFalse{}};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
} }
@ -299,7 +299,7 @@ private:
nonXp = nodep->fhsp(); nonXp = nodep->fhsp();
} else { // Was all X-s } else { // Was all X-s
UINFO(4, " COUNTBITS('x)->0 " << nodep << endl); UINFO(4, " COUNTBITS('x)->0 " << nodep << endl);
AstConst* const newp = new AstConst(nodep->fileline(), AstConst::BitFalse()); AstConst* const newp = new AstConst{nodep->fileline(), AstConst::BitFalse{}};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
return; return;
@ -325,19 +325,19 @@ private:
// CONST(num) -> VARREF(newvarp) // CONST(num) -> VARREF(newvarp)
// -> VAR(newvarp) // -> VAR(newvarp)
// -> INITIAL(VARREF(newvarp, OR(num_No_Xs,AND(random,num_1s_Where_X)) // -> INITIAL(VARREF(newvarp, OR(num_No_Xs,AND(random,num_1s_Where_X))
V3Number numb1(nodep, nodep->width()); V3Number numb1{nodep, nodep->width()};
numb1.opBitsOne(nodep->num()); numb1.opBitsOne(nodep->num());
V3Number numbx(nodep, nodep->width()); V3Number numbx{nodep, nodep->width()};
numbx.opBitsXZ(nodep->num()); numbx.opBitsXZ(nodep->num());
if (!m_allowXUnique || v3Global.opt.xAssign() != "unique") { if (!m_allowXUnique || v3Global.opt.xAssign() != "unique") {
// All X bits just become 0; fastest simulation, but not nice // All X bits just become 0; fastest simulation, but not nice
V3Number numnew(nodep, numb1.width()); V3Number numnew{nodep, numb1.width()};
if (v3Global.opt.xAssign() == "1") { if (v3Global.opt.xAssign() == "1") {
numnew.opOr(numb1, numbx); numnew.opOr(numb1, numbx);
} else { } else {
numnew.opAssign(numb1); numnew.opAssign(numb1);
} }
AstConst* const newp = new AstConst(nodep->fileline(), numnew); AstConst* const newp = new AstConst{nodep->fileline(), numnew};
nodep->replaceWith(newp); nodep->replaceWith(newp);
VL_DO_DANGLING(nodep->deleteTree(), nodep); VL_DO_DANGLING(nodep->deleteTree(), nodep);
UINFO(4, " -> " << newp << endl); UINFO(4, " -> " << newp << endl);
@ -353,18 +353,18 @@ private:
VNRelinker replaceHandle; VNRelinker replaceHandle;
nodep->unlinkFrBack(&replaceHandle); nodep->unlinkFrBack(&replaceHandle);
AstNodeVarRef* const newref1p AstNodeVarRef* const newref1p
= new AstVarRef(nodep->fileline(), newvarp, VAccess::READ); = new AstVarRef{nodep->fileline(), newvarp, VAccess::READ};
replaceHandle.relink(newref1p); // Replace const with varref replaceHandle.relink(newref1p); // Replace const with varref
AstInitial* const newinitp = new AstInitial( AstInitial* const newinitp = new AstInitial{
nodep->fileline(), nodep->fileline(),
new AstAssign( new AstAssign{
nodep->fileline(), nodep->fileline(),
new AstVarRef(nodep->fileline(), newvarp, VAccess::WRITE), new AstVarRef{nodep->fileline(), newvarp, VAccess::WRITE},
new AstOr(nodep->fileline(), new AstConst(nodep->fileline(), numb1), new AstOr{nodep->fileline(), new AstConst{nodep->fileline(), numb1},
new AstAnd(nodep->fileline(), new AstAnd{nodep->fileline(),
new AstConst(nodep->fileline(), numbx), new AstConst{nodep->fileline(), numbx},
new AstRand(nodep->fileline(), AstRand::Reset{}, new AstRand{nodep->fileline(), AstRand::Reset{},
nodep->dtypep(), true))))); nodep->dtypep(), true}}}}};
// Add inits in front of other statement. // Add inits in front of other statement.
// In the future, we should stuff the initp into the module's constructor. // In the future, we should stuff the initp into the module's constructor.
AstNode* const afterp = m_modp->stmtsp()->unlinkFrBackWithNext(); AstNode* const afterp = m_modp->stmtsp()->unlinkFrBackWithNext();
@ -395,10 +395,10 @@ private:
// If (maxmsb >= selected), we're in bound // If (maxmsb >= selected), we're in bound
AstNodeExpr* condp AstNodeExpr* condp
= new AstGte(nodep->fileline(), = new AstGte{nodep->fileline(),
new AstConst(nodep->fileline(), AstConst::WidthedValue(), new AstConst(nodep->fileline(), AstConst::WidthedValue(),
nodep->lsbp()->width(), maxmsb), nodep->lsbp()->width(), maxmsb),
nodep->lsbp()->cloneTree(false)); nodep->lsbp()->cloneTree(false)};
// See if the condition is constant true (e.g. always in bound due to constant select) // See if the condition is constant true (e.g. always in bound due to constant select)
// Note below has null backp(); the Edit function knows how to deal with that. // Note below has null backp(); the Edit function knows how to deal with that.
condp = V3Const::constifyEdit(condp); condp = V3Const::constifyEdit(condp);
@ -409,10 +409,10 @@ private:
// SEL(...) -> COND(LTE(bit<=maxmsb), ARRAYSEL(...), {width{1'bx}}) // SEL(...) -> COND(LTE(bit<=maxmsb), ARRAYSEL(...), {width{1'bx}})
VNRelinker replaceHandle; VNRelinker replaceHandle;
nodep->unlinkFrBack(&replaceHandle); nodep->unlinkFrBack(&replaceHandle);
V3Number xnum(nodep, nodep->width()); V3Number xnum{nodep, nodep->width()};
xnum.setAllBitsX(); xnum.setAllBitsX();
AstNode* const newp = new AstCondBound(nodep->fileline(), condp, nodep, AstNode* const newp = new AstCondBound{nodep->fileline(), condp, nodep,
new AstConst(nodep->fileline(), xnum)); new AstConst{nodep->fileline(), xnum}};
if (debug() >= 9) newp->dumpTree(cout, " _new: "); if (debug() >= 9) newp->dumpTree(cout, " _new: ");
// Link in conditional // Link in conditional
replaceHandle.relink(newp); replaceHandle.relink(newp);
@ -454,10 +454,10 @@ private:
// See if the condition is constant true // See if the condition is constant true
AstNodeExpr* condp AstNodeExpr* condp
= new AstGte(nodep->fileline(), = new AstGte{nodep->fileline(),
new AstConst(nodep->fileline(), AstConst::WidthedValue(), new AstConst(nodep->fileline(), AstConst::WidthedValue{},
nodep->bitp()->width(), declElements - 1), nodep->bitp()->width(), declElements - 1),
nodep->bitp()->cloneTree(false)); nodep->bitp()->cloneTree(false)};
// Note below has null backp(); the Edit function knows how to deal with that. // Note below has null backp(); the Edit function knows how to deal with that.
condp = V3Const::constifyEdit(condp); condp = V3Const::constifyEdit(condp);
if (condp->isOne()) { if (condp->isOne()) {
@ -469,14 +469,14 @@ private:
// ARRAYSEL(...) -> COND(LT(bit<maxbit), ARRAYSEL(...), {width{1'bx}}) // ARRAYSEL(...) -> COND(LT(bit<maxbit), ARRAYSEL(...), {width{1'bx}})
VNRelinker replaceHandle; VNRelinker replaceHandle;
nodep->unlinkFrBack(&replaceHandle); nodep->unlinkFrBack(&replaceHandle);
V3Number xnum(nodep, nodep->width()); V3Number xnum{nodep, nodep->width()};
if (nodep->isString()) { if (nodep->isString()) {
xnum = V3Number{V3Number::String{}, nodep, ""}; xnum = V3Number{V3Number::String{}, nodep, ""};
} else { } else {
xnum.setAllBitsX(); xnum.setAllBitsX();
} }
AstNode* const newp = new AstCondBound(nodep->fileline(), condp, nodep, AstNode* const newp = new AstCondBound{nodep->fileline(), condp, nodep,
new AstConst(nodep->fileline(), xnum)); new AstConst{nodep->fileline(), xnum}};
if (debug() >= 9) newp->dumpTree(cout, " _new: "); if (debug() >= 9) newp->dumpTree(cout, " _new: ");
// Link in conditional, can blow away temp xor // Link in conditional, can blow away temp xor
replaceHandle.relink(newp); replaceHandle.relink(newp);
@ -486,9 +486,9 @@ private:
// ARRAYSEL(...) -> ARRAYSEL(COND(LT(bit<maxbit), bit, 0)) // ARRAYSEL(...) -> ARRAYSEL(COND(LT(bit<maxbit), bit, 0))
VNRelinker replaceHandle; VNRelinker replaceHandle;
AstNodeExpr* const bitp = nodep->bitp()->unlinkFrBack(&replaceHandle); AstNodeExpr* const bitp = nodep->bitp()->unlinkFrBack(&replaceHandle);
AstNodeExpr* const newp = new AstCondBound( AstNodeExpr* const newp = new AstCondBound{
bitp->fileline(), condp, bitp, bitp->fileline(), condp, bitp,
new AstConst(bitp->fileline(), AstConst::WidthedValue(), bitp->width(), 0)); new AstConst{bitp->fileline(), AstConst::WidthedValue{}, bitp->width(), 0}};
// Added X's, tristate them too // Added X's, tristate them too
if (debug() >= 9) newp->dumpTree(cout, " _new: "); if (debug() >= 9) newp->dumpTree(cout, " _new: ");
replaceHandle.relink(newp); replaceHandle.relink(newp);