V3Covergroup: fix coverpoint cleanup for unsupported covergroups
Two bugs fixed: 1. AstCReset: mark as ineligible for coverage expressions via isExprCoverageEligible() override, preventing verilogForTree from being called on CReset nodes (which has no V3EmitV handler). 2. generateCrossCode: when a cross references an unknown coverpoint, don't delete the cross node early. The caller's cleanup loop (in visit(AstClass*)) is responsible for deleting all coverpoints and crosses. Early deletion left a dangling pointer in m_coverCrosses causing a use-after-free segfault. 3. hasUnsupportedEvent path: added coverpoint/cross cleanup before returning so AST nodes don't reach downstream passes (V3EmitCFunc, V3MergeCond) which no longer have stub visitors for them. All 60 covergroup tests now pass. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
This commit is contained in:
parent
14c67621ac
commit
a5f10c9abf
|
|
@ -690,6 +690,7 @@ public:
|
|||
string emitVerilog() override { V3ERROR_NA_RETURN(""); }
|
||||
string emitC() override { V3ERROR_NA_RETURN(""); }
|
||||
bool cleanOut() const override { return true; }
|
||||
bool isExprCoverageEligible() const override { return false; }
|
||||
const char* broken() const override {
|
||||
BROKEN_RTN(!VN_IS(backp(), NodeAssign)); // V3Emit* assumption
|
||||
return nullptr;
|
||||
|
|
|
|||
|
|
@ -1345,8 +1345,7 @@ class FunctionalCoverageVisitor final : public VNVisitor {
|
|||
refp->v3warn(COVERIGN,
|
||||
"Ignoring unsupported: cross references unknown coverpoint: "
|
||||
+ refp->name());
|
||||
// Delete the entire cross since we can't generate it
|
||||
VL_DO_DANGLING(crossp->unlinkFrBack()->deleteTree(), crossp);
|
||||
// Don't delete crossp here - the caller's cleanup loop will delete it
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -1830,7 +1829,19 @@ class FunctionalCoverageVisitor final : public VNVisitor {
|
|||
}
|
||||
|
||||
// If covergroup has unsupported clocking event, skip processing it
|
||||
if (hasUnsupportedEvent) return;
|
||||
// but still clean up coverpoints so they don't reach downstream passes
|
||||
if (hasUnsupportedEvent) {
|
||||
iterateChildren(nodep);
|
||||
for (AstCoverpoint* cpp : m_coverpoints) {
|
||||
cpp->unlinkFrBack();
|
||||
VL_DO_DANGLING(cpp->deleteTree(), cpp);
|
||||
}
|
||||
for (AstCoverCross* crossp : m_coverCrosses) {
|
||||
crossp->unlinkFrBack();
|
||||
VL_DO_DANGLING(crossp->deleteTree(), crossp);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// Find the sample() method and constructor
|
||||
m_sampleFuncp = VN_CAST(m_memberMap.findMember(nodep, "sample"), Func);
|
||||
|
|
|
|||
Loading…
Reference in New Issue