[llvm] f364278 - [FuncSpec][NFC] Cache code metrics for analyzed functions.

Alexandros Lamprineas via llvm-commits llvm-commits at lists.llvm.org
Fri Apr 1 02:59:08 PDT 2022


Author: Alexandros Lamprineas
Date: 2022-04-01T10:58:26+01:00
New Revision: f364278c459c4ed1dfc4e0d16af5af3d23f9ec15

URL: https://github.com/llvm/llvm-project/commit/f364278c459c4ed1dfc4e0d16af5af3d23f9ec15
DIFF: https://github.com/llvm/llvm-project/commit/f364278c459c4ed1dfc4e0d16af5af3d23f9ec15.diff

LOG: [FuncSpec][NFC] Cache code metrics for analyzed functions.

This isn't expected to reduce compilation times as 'max-iters' is set to
one by default, but it helps with recursive functions that require higher
iteration counts.

Differential Revision: https://reviews.llvm.org/D122819

Added: 
    

Modified: 
    llvm/lib/Transforms/IPO/FunctionSpecialization.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Transforms/IPO/FunctionSpecialization.cpp b/llvm/lib/Transforms/IPO/FunctionSpecialization.cpp
index fe8b788c43306..ca10ca99b1531 100644
--- a/llvm/lib/Transforms/IPO/FunctionSpecialization.cpp
+++ b/llvm/lib/Transforms/IPO/FunctionSpecialization.cpp
@@ -21,8 +21,6 @@
 //   but that's off by default under an option.
 // - The cost-model could be further looked into (it mainly focuses on inlining
 //   benefits),
-// - We are not yet caching analysis results, but profiling and checking where
-//   extra compile time is spent didn't suggest this to be a problem.
 //
 // Ideas:
 // - With a function specialization attribute for arguments, we could have
@@ -281,6 +279,7 @@ class FunctionSpecializer {
   SmallPtrSet<Function *, 4> SpecializedFuncs;
   SmallPtrSet<Function *, 4> FullySpecialized;
   SmallVector<Instruction *> ReplacedWithConstant;
+  DenseMap<Function *, CodeMetrics> FunctionMetrics;
 
 public:
   FunctionSpecializer(SCCPSolver &Solver,
@@ -390,6 +389,24 @@ class FunctionSpecializer {
   // also in the cost model.
   unsigned NbFunctionsSpecialized = 0;
 
+  // Compute the code metrics for function \p F.
+  CodeMetrics &analyzeFunction(Function *F) {
+    auto I = FunctionMetrics.insert({F, CodeMetrics()});
+    CodeMetrics &Metrics = I.first->second;
+    if (I.second) {
+      // The code metrics were not cached.
+      SmallPtrSet<const Value *, 32> EphValues;
+      CodeMetrics::collectEphemeralValues(F, &(GetAC)(*F), EphValues);
+      for (BasicBlock &BB : *F)
+        Metrics.analyzeBasicBlock(&BB, (GetTTI)(*F), EphValues);
+
+      LLVM_DEBUG(dbgs() << "FnSpecialization: Code size of function "
+                        << F->getName() << " is " << Metrics.NumInsts
+                        << " instructions\n");
+    }
+    return Metrics;
+  }
+
   /// Clone the function \p F and remove the ssa_copy intrinsics added by
   /// the SCCPSolver in the cloned version.
   Function *cloneCandidateFunction(Function *F, ValueToValueMapTy &Mappings) {
@@ -528,13 +545,7 @@ class FunctionSpecializer {
 
   /// Compute and return the cost of specializing function \p F.
   InstructionCost getSpecializationCost(Function *F) {
-    // Compute the code metrics for the function.
-    SmallPtrSet<const Value *, 32> EphValues;
-    CodeMetrics::collectEphemeralValues(F, &(GetAC)(*F), EphValues);
-    CodeMetrics Metrics;
-    for (BasicBlock &BB : *F)
-      Metrics.analyzeBasicBlock(&BB, (GetTTI)(*F), EphValues);
-
+    CodeMetrics &Metrics = analyzeFunction(F);
     // If the code metrics reveal that we shouldn't duplicate the function, we
     // shouldn't specialize it. Set the specialization cost to Invalid.
     // Or if the lines of codes implies that this function is easy to get


        


More information about the llvm-commits mailing list