diff --git a/llvm/include/llvm/Analysis/LazyCallGraph.h b/llvm/include/llvm/Analysis/LazyCallGraph.h index 68c98b416ce96..ac8ca207d312b 100644 --- a/llvm/include/llvm/Analysis/LazyCallGraph.h +++ b/llvm/include/llvm/Analysis/LazyCallGraph.h @@ -943,6 +943,11 @@ class LazyCallGraph { LazyCallGraph(LazyCallGraph &&G); LazyCallGraph &operator=(LazyCallGraph &&RHS); +#if !defined(NDEBUG) || defined(EXPENSIVE_CHECKS) + /// Verify that every RefSCC is valid. + void verify(); +#endif + bool invalidate(Module &, const PreservedAnalyses &PA, ModuleAnalysisManager::Invalidator &); diff --git a/llvm/lib/Analysis/CGSCCPassManager.cpp b/llvm/lib/Analysis/CGSCCPassManager.cpp index 2246887afe68a..8ae5c3dee6103 100644 --- a/llvm/lib/Analysis/CGSCCPassManager.cpp +++ b/llvm/lib/Analysis/CGSCCPassManager.cpp @@ -340,6 +340,11 @@ ModuleToPostOrderCGSCCPassAdaptor::run(Module &M, ModuleAnalysisManager &AM) { } while (!RCWorklist.empty()); } +#if defined(EXPENSIVE_CHECKS) + // Verify that the call graph is still valid. + CG.verify(); +#endif + // By definition we preserve the call garph, all SCC analyses, and the // analysis proxies by handling them above and in any nested pass managers. PA.preserveSet>(); diff --git a/llvm/lib/Analysis/LazyCallGraph.cpp b/llvm/lib/Analysis/LazyCallGraph.cpp index 1e5cf84d589b0..48a7ca0061600 100644 --- a/llvm/lib/Analysis/LazyCallGraph.cpp +++ b/llvm/lib/Analysis/LazyCallGraph.cpp @@ -211,6 +211,14 @@ LazyCallGraph::LazyCallGraph(LazyCallGraph &&G) updateGraphPtrs(); } +#if !defined(NDEBUG) || defined(EXPENSIVE_CHECKS) +void LazyCallGraph::verify() { + for (RefSCC &RC : postorder_ref_sccs()) { + RC.verify(); + } +} +#endif + bool LazyCallGraph::invalidate(Module &, const PreservedAnalyses &PA, ModuleAnalysisManager::Invalidator &) { // Check whether the analysis, all analyses on functions, or the function's