diff --git a/llvm/include/llvm/Analysis/InlineAdvisor.h b/llvm/include/llvm/Analysis/InlineAdvisor.h --- a/llvm/include/llvm/Analysis/InlineAdvisor.h +++ b/llvm/include/llvm/Analysis/InlineAdvisor.h @@ -9,6 +9,7 @@ #ifndef LLVM_ANALYSIS_INLINEADVISOR_H #define LLVM_ANALYSIS_INLINEADVISOR_H +#include "llvm/Analysis/CGSCCPassManager.h" #include "llvm/Analysis/InlineCost.h" #include "llvm/Analysis/LazyCallGraph.h" #include "llvm/Config/llvm-config.h" @@ -271,6 +272,9 @@ explicit InlineAdvisorAnalysisPrinterPass(raw_ostream &OS) : OS(OS) {} PreservedAnalyses run(Module &M, ModuleAnalysisManager &MAM); + + PreservedAnalyses run(LazyCallGraph::SCC &InitialC, CGSCCAnalysisManager &AM, + LazyCallGraph &CG, CGSCCUpdateResult &UR); }; std::unique_ptr diff --git a/llvm/lib/Analysis/InlineAdvisor.cpp b/llvm/lib/Analysis/InlineAdvisor.cpp --- a/llvm/lib/Analysis/InlineAdvisor.cpp +++ b/llvm/lib/Analysis/InlineAdvisor.cpp @@ -630,3 +630,22 @@ IA->getAdvisor()->print(OS); return PreservedAnalyses::all(); } + +PreservedAnalyses InlineAdvisorAnalysisPrinterPass::run( + LazyCallGraph::SCC &InitialC, CGSCCAnalysisManager &AM, LazyCallGraph &CG, + CGSCCUpdateResult &UR) { + const auto &MAMProxy = + AM.getResult(InitialC, CG); + + if (InitialC.size() == 0) { + OS << "SCC is empty!\n"; + return PreservedAnalyses::all(); + } + Module &M = *InitialC.begin()->getFunction().getParent(); + const auto *IA = MAMProxy.getCachedResult(M); + if (!IA) + OS << "No Inline Advisor\n"; + else + IA->getAdvisor()->print(OS); + return PreservedAnalyses::all(); +} diff --git a/llvm/lib/Transforms/IPO/Inliner.cpp b/llvm/lib/Transforms/IPO/Inliner.cpp --- a/llvm/lib/Transforms/IPO/Inliner.cpp +++ b/llvm/lib/Transforms/IPO/Inliner.cpp @@ -105,6 +105,11 @@ static cl::opt KeepAdvisorForPrinting("keep-inline-advisor-for-printing", cl::init(false), cl::Hidden); +/// Allows printing the contents of the advisor after each SCC inliner pass. +static cl::opt + EnablePostSCCAdvisorPrinting("enable-scc-inline-advisor-printing", + cl::init(false), cl::Hidden); + extern cl::opt InlinerFunctionImportStats; static cl::opt CGSCCInlineReplayFile( @@ -1114,9 +1119,14 @@ // into the callers so that our optimizations can reflect that. // For PreLinkThinLTO pass, we disable hot-caller heuristic for sample PGO // because it makes profile annotation in the backend inaccurate. - if (MandatoryFirst) + if (MandatoryFirst) { PM.addPass(InlinerPass(/*OnlyMandatory*/ true)); + if (EnablePostSCCAdvisorPrinting) + PM.addPass(InlineAdvisorAnalysisPrinterPass(dbgs())); + } PM.addPass(InlinerPass()); + if (EnablePostSCCAdvisorPrinting) + PM.addPass(InlineAdvisorAnalysisPrinterPass(dbgs())); } PreservedAnalyses ModuleInlinerWrapperPass::run(Module &M, diff --git a/llvm/test/Transforms/Inline/enable-inline-advisor-printing-ml.ll b/llvm/test/Transforms/Inline/enable-inline-advisor-printing-ml.ll new file mode 100644 --- /dev/null +++ b/llvm/test/Transforms/Inline/enable-inline-advisor-printing-ml.ll @@ -0,0 +1,40 @@ +; REQUIRES: llvm_inliner_model_autogenerated + +; RUN: opt -enable-ml-inliner=release -passes=scc-oz-module-inliner \ +; RUN: -keep-inline-advisor-for-printing \ +; RUN: -enable-scc-inline-advisor-printing -S < %s 2>&1 | FileCheck %s + +; RUN: opt -enable-ml-inliner=release -passes=scc-oz-module-inliner \ +; RUN: -keep-inline-advisor-for-printing -mandatory-inlining-first=0 \ +; RUN: -enable-scc-inline-advisor-printing -S < %s 2>&1 \ +; RUN: | FileCheck %s --check-prefix=TWO + +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +define dso_local noundef i32 @_Z3fooi(i32 noundef %y) { +entry: + ret i32 %y +} + +define dso_local noundef i32 @main(i32 noundef %argc, ptr noundef %argv) { +entry: + %call = call noundef i32 @_Z3fooi(i32 noundef %argc) + ret i32 %call +} + +; CHECK: [MLInlineAdvisor] Nodes: +; CHECK-SAME: 2 Edges: 1 +; CHECK: [MLInlineAdvisor] Nodes: +; CHECK-SAME: 2 Edges: 1 +; CHECK: [MLInlineAdvisor] Nodes: +; CHECK-SAME: 2 Edges: 1 +; CHECK: [MLInlineAdvisor] Nodes: +; CHECK-SAME: 2 Edges: 0 +; CHECK-NOT: [MLInlineAdvisor] Nodes: + +; TWO: [MLInlineAdvisor] Nodes: +; TWO-SAME: 2 Edges: 1 +; TWO: [MLInlineAdvisor] Nodes: +; TWO-SAME: 2 Edges: 0 +; TWO-NOT: [MLInlineAdvisor] Nodes: diff --git a/llvm/test/Transforms/Inline/enable-inline-advisor-printing.ll b/llvm/test/Transforms/Inline/enable-inline-advisor-printing.ll new file mode 100644 --- /dev/null +++ b/llvm/test/Transforms/Inline/enable-inline-advisor-printing.ll @@ -0,0 +1,18 @@ +; RUN: opt -passes=inliner-wrapper -keep-inline-advisor-for-printing \ +; RUN: -enable-scc-inline-advisor-printing -S < %s 2>&1 | FileCheck %s + +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +define dso_local noundef i32 @_Z3fooi(i32 noundef %y) { +entry: + ret i32 %y +} + +define dso_local noundef i32 @main(i32 noundef %argc, ptr noundef %argv) { +entry: + %call = call noundef i32 @_Z3fooi(i32 noundef %argc) + ret i32 %call +} + +; CHECK-COUNT-4: Unimplemented InlineAdvisor print