[polly] r254150 - IR cleanup after CodeGeneration

Michael Kruse via llvm-commits llvm-commits at lists.llvm.org
Thu Nov 26 04:36:26 PST 2015


Author: meinersbur
Date: Thu Nov 26 06:36:25 2015
New Revision: 254150

URL: http://llvm.org/viewvc/llvm-project?rev=254150&view=rev
Log:
IR cleanup after CodeGeneration

Re-run canonicalization passes after Polly's code generation.

The set of passes currently added here are nearly all the passes between
--polly-position=early and --polly-position=before-vectorizer, i.e. all
passes that would usually run after Polly.

In order to run these only if Polly actually modified the code, we add a
function attribute "polly-optimzed" to a function that contains
generated code. The cleanup pass is skipped if the function does not
have this attribute.

There is no support by the (legacy) PassManager to run passes only under
some conditions. One could have wrapped all transformation passes to run
only when CodeGeneration changed the code, but the analyses would run
anyway. This patch creates an independent pass manager. The
disadvantages are that all analyses have to re-run even if preserved and
it does not honor compiler switches like the PassManagerBuilder does.

Differential Revision: http://reviews.llvm.org/D14333

Added:
    polly/trunk/include/polly/CodeGen/CodegenCleanup.h
    polly/trunk/lib/CodeGen/CodegenCleanup.cpp
Modified:
    polly/trunk/lib/CMakeLists.txt
    polly/trunk/lib/CodeGen/CodeGeneration.cpp
    polly/trunk/lib/Support/RegisterPasses.cpp

Added: polly/trunk/include/polly/CodeGen/CodegenCleanup.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/include/polly/CodeGen/CodegenCleanup.h?rev=254150&view=auto
==============================================================================
--- polly/trunk/include/polly/CodeGen/CodegenCleanup.h (added)
+++ polly/trunk/include/polly/CodeGen/CodegenCleanup.h Thu Nov 26 06:36:25 2015
@@ -0,0 +1,17 @@
+#ifndef POLLY_CODEGENCLEANUP_H
+#define POLLY_CODEGENCLEANUP_H
+
+namespace llvm {
+class FunctionPass;
+class PassRegistry;
+}
+
+namespace polly {
+llvm::FunctionPass *createCodegenCleanupPass();
+}
+
+namespace llvm {
+void initializeCodegenCleanupPass(llvm::PassRegistry &);
+}
+
+#endif

Modified: polly/trunk/lib/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/CMakeLists.txt?rev=254150&r1=254149&r2=254150&view=diff
==============================================================================
--- polly/trunk/lib/CMakeLists.txt (original)
+++ polly/trunk/lib/CMakeLists.txt Thu Nov 26 06:36:25 2015
@@ -37,6 +37,7 @@ add_polly_library(Polly
   CodeGen/IRBuilder.cpp
   CodeGen/Utils.cpp
   CodeGen/RuntimeDebugBuilder.cpp
+  CodeGen/CodegenCleanup.cpp
   ${GPGPU_CODEGEN_FILES}
   Exchange/JSONExporter.cpp
   Support/GICHelper.cpp

Modified: polly/trunk/lib/CodeGen/CodeGeneration.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/CodeGen/CodeGeneration.cpp?rev=254150&r1=254149&r2=254150&view=diff
==============================================================================
--- polly/trunk/lib/CodeGen/CodeGeneration.cpp (original)
+++ polly/trunk/lib/CodeGen/CodeGeneration.cpp Thu Nov 26 06:36:25 2015
@@ -176,6 +176,12 @@ public:
 
     assert(!verifyGeneratedFunction(S, *EnteringBB->getParent()) &&
            "Verification of generated function failed");
+
+    // Mark the function such that we run additional cleanup passes on this
+    // function (e.g. mem2reg to rediscover phi nodes).
+    Function *F = EnteringBB->getParent();
+    F->addFnAttr("polly-optimized");
+
     return true;
   }
 

Added: polly/trunk/lib/CodeGen/CodegenCleanup.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/CodeGen/CodegenCleanup.cpp?rev=254150&view=auto
==============================================================================
--- polly/trunk/lib/CodeGen/CodegenCleanup.cpp (added)
+++ polly/trunk/lib/CodeGen/CodegenCleanup.cpp Thu Nov 26 06:36:25 2015
@@ -0,0 +1,121 @@
+#include "polly/CodeGen/CodegenCleanup.h"
+
+#include "llvm/Analysis/CFLAliasAnalysis.h"
+#include "llvm/Analysis/ScopedNoAliasAA.h"
+#include "llvm/Analysis/TypeBasedAliasAnalysis.h"
+#include "llvm/IR/Function.h"
+#include "llvm/IR/LegacyPassManager.h"
+#include "llvm/PassInfo.h"
+#include "llvm/PassRegistry.h"
+#include "llvm/PassSupport.h"
+#include "llvm/Support/Debug.h"
+#include "llvm/Transforms/Scalar.h"
+#define DEBUG_TYPE "polly-cleanup"
+
+using namespace llvm;
+using namespace polly;
+
+namespace {
+
+class CodegenCleanup : public FunctionPass {
+private:
+  CodegenCleanup(const CodegenCleanup &) = delete;
+  const CodegenCleanup &operator=(const CodegenCleanup &) = delete;
+
+  llvm::legacy::FunctionPassManager *FPM;
+
+public:
+  static char ID;
+  explicit CodegenCleanup() : FunctionPass(ID), FPM(nullptr) {}
+
+  /// @name FunctionPass interface
+  //@{
+  virtual void getAnalysisUsage(llvm::AnalysisUsage &AU) const override {}
+
+  virtual bool doInitialization(Module &M) override {
+    assert(!FPM);
+
+    FPM = new llvm::legacy::FunctionPassManager(&M);
+
+    // TODO: How to make parent passes discoverable?
+    // TODO: Should be sensitive to compiler options in PassManagerBuilder, to
+    // which wo do not have access here.
+    FPM->add(createCFLAAWrapperPass());
+    FPM->add(createScopedNoAliasAAWrapperPass());
+    FPM->add(createTypeBasedAAWrapperPass());
+    FPM->add(createAAResultsWrapperPass());
+
+    // TODO: These are non-conditional passes that run between
+    // EP_ModuleOptimizerEarly and EP_VectorizerStart just to ensure we do not
+    // miss any optimization that would have run after Polly with
+    // -polly-position=early. This can probably be reduced to a more compact set
+    // of passes.
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createScalarReplAggregatesPass());
+    FPM->add(createEarlyCSEPass());
+    FPM->add(createInstructionCombiningPass());
+    FPM->add(createJumpThreadingPass());
+    FPM->add(createCorrelatedValuePropagationPass());
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createInstructionCombiningPass());
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createReassociatePass());
+    FPM->add(createLoopRotatePass());
+    FPM->add(createLICMPass());
+    FPM->add(createLoopUnswitchPass());
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createInstructionCombiningPass());
+    FPM->add(createIndVarSimplifyPass());
+    FPM->add(createLoopIdiomPass());
+    FPM->add(createLoopDeletionPass());
+    FPM->add(createLoopInterchangePass());
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createSimpleLoopUnrollPass());
+    FPM->add(createMergedLoadStoreMotionPass());
+    FPM->add(createMemCpyOptPass());
+    FPM->add(createBitTrackingDCEPass());
+    FPM->add(createInstructionCombiningPass());
+    FPM->add(createJumpThreadingPass());
+    FPM->add(createCorrelatedValuePropagationPass());
+    FPM->add(createDeadStoreEliminationPass());
+    FPM->add(createLICMPass());
+    FPM->add(createLoopRerollPass());
+    FPM->add(createLoadCombinePass());
+    FPM->add(createAggressiveDCEPass());
+    FPM->add(createCFGSimplificationPass());
+    FPM->add(createInstructionCombiningPass());
+
+    return FPM->doInitialization();
+  }
+
+  virtual bool doFinalization(Module &M) override {
+    bool Result = FPM->doFinalization();
+
+    delete FPM;
+    FPM = nullptr;
+
+    return Result;
+  }
+
+  virtual bool runOnFunction(llvm::Function &F) override {
+    if (!F.hasFnAttribute("polly-optimized")) {
+      DEBUG(dbgs() << F.getName()
+                   << ": Skipping cleanup because Polly did not optimize it.");
+      return false;
+    }
+
+    DEBUG(dbgs() << F.getName() << ": Running codegen cleanup...");
+    return FPM->run(F);
+  }
+  //@}
+};
+
+char CodegenCleanup::ID;
+}
+
+FunctionPass *polly::createCodegenCleanupPass() { return new CodegenCleanup(); }
+
+INITIALIZE_PASS_BEGIN(CodegenCleanup, "polly-cleanup",
+                      "Polly - Cleanup after code generation", false, false)
+INITIALIZE_PASS_END(CodegenCleanup, "polly-cleanup",
+                    "Polly - Cleanup after code generation", false, false)

Modified: polly/trunk/lib/Support/RegisterPasses.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Support/RegisterPasses.cpp?rev=254150&r1=254149&r2=254150&view=diff
==============================================================================
--- polly/trunk/lib/Support/RegisterPasses.cpp (original)
+++ polly/trunk/lib/Support/RegisterPasses.cpp Thu Nov 26 06:36:25 2015
@@ -22,6 +22,7 @@
 #include "polly/RegisterPasses.h"
 #include "polly/Canonicalization.h"
 #include "polly/CodeGen/CodeGeneration.h"
+#include "polly/CodeGen/CodegenCleanup.h"
 #include "polly/DependenceInfo.h"
 #include "polly/LinkAllPasses.h"
 #include "polly/Options.h"
@@ -153,6 +154,7 @@ void initializePollyPasses(PassRegistry
   initializePollyCanonicalizePass(Registry);
   initializeScopDetectionPass(Registry);
   initializeScopInfoPass(Registry);
+  initializeCodegenCleanupPass(Registry);
 }
 
 /// @brief Register Polly passes such that they form a polyhedral optimizer.
@@ -263,7 +265,7 @@ registerPollyLoopOptimizerEndPasses(cons
 
   PM.add(polly::createCodePreparationPass());
   polly::registerPollyPasses(PM);
-  // TODO: Add some cleanup passes
+  PM.add(createCodegenCleanupPass());
 }
 
 static void
@@ -277,7 +279,7 @@ registerPollyScalarOptimizerLatePasses(c
 
   PM.add(polly::createCodePreparationPass());
   polly::registerPollyPasses(PM);
-  // TODO: Add some cleanup passes
+  PM.add(createCodegenCleanupPass());
 }
 
 /// @brief Register Polly to be available as an optimizer




More information about the llvm-commits mailing list