Inliner.h 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. #pragma once
  2. #ifdef __GNUC__
  3. #pragma GCC diagnostic push
  4. #pragma GCC diagnostic ignored "-Wunused-parameter"
  5. #endif
  6. //===- Inliner.h - Inliner pass and infrastructure --------------*- C++ -*-===//
  7. //
  8. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  9. // See https://llvm.org/LICENSE.txt for license information.
  10. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  11. //
  12. //===----------------------------------------------------------------------===//
  13. #ifndef LLVM_TRANSFORMS_IPO_INLINER_H
  14. #define LLVM_TRANSFORMS_IPO_INLINER_H
  15. #include "llvm/Analysis/CGSCCPassManager.h"
  16. #include "llvm/Analysis/CallGraphSCCPass.h"
  17. #include "llvm/Analysis/InlineAdvisor.h"
  18. #include "llvm/Analysis/InlineCost.h"
  19. #include "llvm/Analysis/LazyCallGraph.h"
  20. #include "llvm/Analysis/Utils/ImportedFunctionsInliningStatistics.h"
  21. #include "llvm/IR/PassManager.h"
  22. namespace llvm {
  23. class AssumptionCacheTracker;
  24. class CallGraph;
  25. class ProfileSummaryInfo;
  26. /// This class contains all of the helper code which is used to perform the
  27. /// inlining operations that do not depend on the policy. It contains the core
  28. /// bottom-up inlining infrastructure that specific inliner passes use.
  29. struct LegacyInlinerBase : public CallGraphSCCPass {
  30. explicit LegacyInlinerBase(char &ID);
  31. explicit LegacyInlinerBase(char &ID, bool InsertLifetime);
  32. /// For this class, we declare that we require and preserve the call graph.
  33. /// If the derived class implements this method, it should always explicitly
  34. /// call the implementation here.
  35. void getAnalysisUsage(AnalysisUsage &Info) const override;
  36. using llvm::Pass::doInitialization;
  37. bool doInitialization(CallGraph &CG) override;
  38. /// Main run interface method, this implements the interface required by the
  39. /// Pass class.
  40. bool runOnSCC(CallGraphSCC &SCC) override;
  41. using llvm::Pass::doFinalization;
  42. /// Remove now-dead linkonce functions at the end of processing to avoid
  43. /// breaking the SCC traversal.
  44. bool doFinalization(CallGraph &CG) override;
  45. /// This method must be implemented by the subclass to determine the cost of
  46. /// inlining the specified call site. If the cost returned is greater than
  47. /// the current inline threshold, the call site is not inlined.
  48. virtual InlineCost getInlineCost(CallBase &CB) = 0;
  49. /// Remove dead functions.
  50. ///
  51. /// This also includes a hack in the form of the 'AlwaysInlineOnly' flag
  52. /// which restricts it to deleting functions with an 'AlwaysInline'
  53. /// attribute. This is useful for the InlineAlways pass that only wants to
  54. /// deal with that subset of the functions.
  55. bool removeDeadFunctions(CallGraph &CG, bool AlwaysInlineOnly = false);
  56. /// This function performs the main work of the pass. The default of
  57. /// Inlinter::runOnSCC() calls skipSCC() before calling this method, but
  58. /// derived classes which cannot be skipped can override that method and call
  59. /// this function unconditionally.
  60. bool inlineCalls(CallGraphSCC &SCC);
  61. private:
  62. // Insert @llvm.lifetime intrinsics.
  63. bool InsertLifetime = true;
  64. protected:
  65. AssumptionCacheTracker *ACT;
  66. ProfileSummaryInfo *PSI;
  67. std::function<const TargetLibraryInfo &(Function &)> GetTLI;
  68. ImportedFunctionsInliningStatistics ImportedFunctionsStats;
  69. };
  70. /// The inliner pass for the new pass manager.
  71. ///
  72. /// This pass wires together the inlining utilities and the inline cost
  73. /// analysis into a CGSCC pass. It considers every call in every function in
  74. /// the SCC and tries to inline if profitable. It can be tuned with a number of
  75. /// parameters to control what cost model is used and what tradeoffs are made
  76. /// when making the decision.
  77. ///
  78. /// It should be noted that the legacy inliners do considerably more than this
  79. /// inliner pass does. They provide logic for manually merging allocas, and
  80. /// doing considerable DCE including the DCE of dead functions. This pass makes
  81. /// every attempt to be simpler. DCE of functions requires complex reasoning
  82. /// about comdat groups, etc. Instead, it is expected that other more focused
  83. /// passes be composed to achieve the same end result.
  84. class InlinerPass : public PassInfoMixin<InlinerPass> {
  85. public:
  86. InlinerPass(bool OnlyMandatory = false,
  87. ThinOrFullLTOPhase LTOPhase = ThinOrFullLTOPhase::None)
  88. : OnlyMandatory(OnlyMandatory), LTOPhase(LTOPhase) {}
  89. InlinerPass(InlinerPass &&Arg) = default;
  90. PreservedAnalyses run(LazyCallGraph::SCC &C, CGSCCAnalysisManager &AM,
  91. LazyCallGraph &CG, CGSCCUpdateResult &UR);
  92. void printPipeline(raw_ostream &OS,
  93. function_ref<StringRef(StringRef)> MapClassName2PassName);
  94. private:
  95. InlineAdvisor &getAdvisor(const ModuleAnalysisManagerCGSCCProxy::Result &MAM,
  96. FunctionAnalysisManager &FAM, Module &M);
  97. std::unique_ptr<InlineAdvisor> OwnedAdvisor;
  98. const bool OnlyMandatory;
  99. const ThinOrFullLTOPhase LTOPhase;
  100. };
  101. /// Module pass, wrapping the inliner pass. This works in conjunction with the
  102. /// InlineAdvisorAnalysis to facilitate inlining decisions taking into account
  103. /// module-wide state, that need to keep track of inter-inliner pass runs, for
  104. /// a given module. An InlineAdvisor is configured and kept alive for the
  105. /// duration of the ModuleInlinerWrapperPass::run.
  106. class ModuleInlinerWrapperPass
  107. : public PassInfoMixin<ModuleInlinerWrapperPass> {
  108. public:
  109. ModuleInlinerWrapperPass(
  110. InlineParams Params = getInlineParams(), bool MandatoryFirst = true,
  111. InlineContext IC = {},
  112. InliningAdvisorMode Mode = InliningAdvisorMode::Default,
  113. unsigned MaxDevirtIterations = 0);
  114. ModuleInlinerWrapperPass(ModuleInlinerWrapperPass &&Arg) = default;
  115. PreservedAnalyses run(Module &, ModuleAnalysisManager &);
  116. /// Allow adding more CGSCC passes, besides inlining. This should be called
  117. /// before run is called, as part of pass pipeline building.
  118. CGSCCPassManager &getPM() { return PM; }
  119. /// Add a module pass that runs before the CGSCC passes.
  120. template <class T> void addModulePass(T Pass) {
  121. MPM.addPass(std::move(Pass));
  122. }
  123. /// Add a module pass that runs after the CGSCC passes.
  124. template <class T> void addLateModulePass(T Pass) {
  125. AfterCGMPM.addPass(std::move(Pass));
  126. }
  127. void printPipeline(raw_ostream &OS,
  128. function_ref<StringRef(StringRef)> MapClassName2PassName);
  129. private:
  130. const InlineParams Params;
  131. const InlineContext IC;
  132. const InliningAdvisorMode Mode;
  133. const unsigned MaxDevirtIterations;
  134. // TODO: Clean this up so we only have one ModulePassManager.
  135. CGSCCPassManager PM;
  136. ModulePassManager MPM;
  137. ModulePassManager AfterCGMPM;
  138. };
  139. } // end namespace llvm
  140. #endif // LLVM_TRANSFORMS_IPO_INLINER_H
  141. #ifdef __GNUC__
  142. #pragma GCC diagnostic pop
  143. #endif