RefSCC &TargetRC = TargetC.getOuterRefSCC();
(void)TargetRC;
// TODO: This only allows trivial edges to be added for now.
+#ifdef EXPENSIVE_CHECKS
assert((RC == &TargetRC ||
RC->isAncestorOf(TargetRC)) && "New ref edge is not trivial!");
+#endif
RC->insertTrivialRefEdge(N, *RefTarget);
}
RefSCC &TargetRC = TargetC.getOuterRefSCC();
(void)TargetRC;
// TODO: This only allows trivial edges to be added for now.
+#ifdef EXPENSIVE_CHECKS
assert((RC == &TargetRC ||
RC->isAncestorOf(TargetRC)) && "New call edge is not trivial!");
+#endif
// Add a trivial ref edge to be promoted later on alongside
// PromotedRefTargets.
RC->insertTrivialRefEdge(N, *CallTarget);
// The easy case is when the target RefSCC is not this RefSCC. This is
// only supported when the target RefSCC is a child of this RefSCC.
if (&TargetRC != RC) {
+#ifdef EXPENSIVE_CHECKS
assert(RC->isAncestorOf(TargetRC) &&
"Cannot potentially form RefSCC cycles here!");
+#endif
RC->switchOutgoingEdgeToRef(N, *RefTarget);
LLVM_DEBUG(dbgs() << "Switch outgoing call edge to a ref edge from '" << N
<< "' to '" << *RefTarget << "'\n");
// The easy case is when the target RefSCC is not this RefSCC. This is
// only supported when the target RefSCC is a child of this RefSCC.
if (&TargetRC != RC) {
+#ifdef EXPENSIVE_CHECKS
assert(RC->isAncestorOf(TargetRC) &&
"Cannot potentially form RefSCC cycles here!");
+#endif
RC->switchOutgoingEdgeToCall(N, *CallTarget);
LLVM_DEBUG(dbgs() << "Switch outgoing ref edge to a call edge from '" << N
<< "' to '" << *CallTarget << "'\n");
assert(!(*SourceN)[TargetN].isCall() && "Must start with a ref edge!");
SmallVector<SCC *, 1> DeletedSCCs;
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and when this
- // routine finishes.
+#ifdef EXPENSIVE_CHECKS
verify();
auto VerifyOnExit = make_scope_exit([&]() { verify(); });
#endif
// Compute the SCCs which (transitively) reach the source.
auto ComputeSourceConnectedSet = [&](SmallPtrSetImpl<SCC *> &ConnectedSet) {
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
// Check that the RefSCC is still valid before computing this as the
// results will be nonsensical of we've broken its invariants.
verify();
// but because this is forward connectivity we just "recurse" through the
// edges.
auto ComputeTargetConnectedSet = [&](SmallPtrSetImpl<SCC *> &ConnectedSet) {
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
// Check that the RefSCC is still valid before computing this as the
// results will be nonsensical of we've broken its invariants.
verify();
return false; // No new cycle.
}
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
// Before merging, check that the RefSCC remains valid after all the
// postorder updates.
verify();
Node &TargetN) {
assert((*SourceN)[TargetN].isCall() && "Must start with a call edge!");
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and when this
- // routine finishes.
+#ifdef EXPENSIVE_CHECKS
verify();
auto VerifyOnExit = make_scope_exit([&]() { verify(); });
#endif
LazyCallGraph::RefSCC::switchInternalEdgeToRef(Node &SourceN, Node &TargetN) {
assert((*SourceN)[TargetN].isCall() && "Must start with a call edge!");
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and when this
- // routine finishes.
+#ifdef EXPENSIVE_CHECKS
verify();
auto VerifyOnExit = make_scope_exit([&]() { verify(); });
#endif
// just flip the edge here.
SourceN->setEdgeKind(TargetN, Edge::Call);
-#ifndef NDEBUG
- // Check that the RefSCC is still valid.
+#ifdef EXPENSIVE_CHECKS
verify();
#endif
}
// just flip the edge here.
SourceN->setEdgeKind(TargetN, Edge::Ref);
-#ifndef NDEBUG
- // Check that the RefSCC is still valid.
+#ifdef EXPENSIVE_CHECKS
verify();
#endif
}
SourceN->insertEdgeInternal(TargetN, Edge::Ref);
-#ifndef NDEBUG
- // Check that the RefSCC is still valid.
+#ifdef EXPENSIVE_CHECKS
verify();
#endif
}
"Target must be a descendant of the Source.");
#endif
-#ifndef NDEBUG
- // Check that the RefSCC is still valid.
+#ifdef EXPENSIVE_CHECKS
verify();
#endif
}
SmallVector<RefSCC *, 1> DeletedRefSCCs;
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and when this
- // routine finishes.
+#ifdef EXPENSIVE_CHECKS
verify();
auto VerifyOnExit = make_scope_exit([&]() { verify(); });
#endif
assert(G->lookupRefSCC(TargetN) != this &&
"The target must not be a member of this RefSCC");
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and when this
- // routine finishes.
+#ifdef EXPENSIVE_CHECKS
verify();
auto VerifyOnExit = make_scope_exit([&]() { verify(); });
#endif
// We return a list of the resulting *new* RefSCCs in post-order.
SmallVector<RefSCC *, 1> Result;
-#ifndef NDEBUG
- // In a debug build, verify the RefSCC is valid to start with and that either
- // we return an empty list of result RefSCCs and this RefSCC remains valid,
- // or we return new RefSCCs and this RefSCC is dead.
+#ifdef EXPENSIVE_CHECKS
+ // Verify the RefSCC is valid to start with and that either we return an empty
+ // list of result RefSCCs and this RefSCC remains valid, or we return new
+ // RefSCCs and this RefSCC is dead.
verify();
auto VerifyOnExit = make_scope_exit([&]() {
// If we didn't replace our RefSCC with new ones, check that this one
SCCs.clear();
SCCIndices.clear();
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
// Verify the new RefSCCs we've built.
for (RefSCC *RC : Result)
RC->verify();
void LazyCallGraph::RefSCC::insertTrivialCallEdge(Node &SourceN,
Node &TargetN) {
-#ifndef NDEBUG
- // Check that the RefSCC is still valid when we finish.
+#ifdef EXPENSIVE_CHECKS
auto ExitVerifier = make_scope_exit([this] { verify(); });
-#ifdef EXPENSIVE_CHECKS
// Check that we aren't breaking some invariants of the SCC graph. Note that
// this is quadratic in the number of edges in the call graph!
SCC &SourceC = *G->lookupSCC(SourceN);
if (&SourceC != &TargetC)
assert(SourceC.isAncestorOf(TargetC) &&
"Call edge is not trivial in the SCC graph!");
-#endif // EXPENSIVE_CHECKS
-#endif // NDEBUG
+#endif
// First insert it into the source or find the existing edge.
auto InsertResult =
}
void LazyCallGraph::RefSCC::insertTrivialRefEdge(Node &SourceN, Node &TargetN) {
-#ifndef NDEBUG
- // Check that the RefSCC is still valid when we finish.
+#ifdef EXPENSIVE_CHECKS
auto ExitVerifier = make_scope_exit([this] { verify(); });
-#ifdef EXPENSIVE_CHECKS
// Check that we aren't breaking some invariants of the RefSCC graph.
RefSCC &SourceRC = *G->lookupRefSCC(SourceN);
RefSCC &TargetRC = *G->lookupRefSCC(TargetN);
if (&SourceRC != &TargetRC)
assert(SourceRC.isAncestorOf(TargetRC) &&
"Ref edge is not trivial in the RefSCC graph!");
-#endif // EXPENSIVE_CHECKS
-#endif // NDEBUG
+#endif
// First insert it into the source or find the existing edge.
auto InsertResult =
void LazyCallGraph::RefSCC::replaceNodeFunction(Node &N, Function &NewF) {
Function &OldF = N.getFunction();
-#ifndef NDEBUG
- // Check that the RefSCC is still valid when we finish.
+#ifdef EXPENSIVE_CHECKS
auto ExitVerifier = make_scope_exit([this] { verify(); });
assert(G->lookupRefSCC(N) == this &&
SCC *OriginalC = lookupSCC(OriginalN);
RefSCC *OriginalRC = lookupRefSCC(OriginalN);
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
OriginalRC->verify();
auto VerifyOnExit = make_scope_exit([&]() { OriginalRC->verify(); });
#endif
Node &OriginalN = get(OriginalFunction);
RefSCC *OriginalRC = lookupRefSCC(OriginalN);
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
OriginalRC->verify();
auto VerifyOnExit = make_scope_exit([&]() {
OriginalRC->verify();
-#ifdef EXPENSIVE_CHECKS
for (Function *NewFunction : NewFunctions)
lookupRefSCC(get(*NewFunction))->verify();
-#endif
});
#endif
(void)Inserted;
assert(Inserted && "Cannot already have this RefSCC in the index map!");
PostOrderRefSCCs.push_back(NewRC);
-#ifndef NDEBUG
+#ifdef EXPENSIVE_CHECKS
NewRC->verify();
#endif
});