[PATCH] D129352: [CodeGen] Limit building time for CodeGenPrepare

Xiang Zhang via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Jul 8 01:01:00 PDT 2022


xiangzhangllvm created this revision.
Herald added a subscriber: hiraditya.
Herald added a project: All.
xiangzhangllvm requested review of this revision.
Herald added a project: LLVM.
Herald added a subscriber: llvm-commits.

Currently CodeGenPrepare is very time consuming in handling big functions.

**Old Algorithm** :
It iterate very BB in function, and go on handle very instructions in BB.
Due to some instruction optimizations may affect the BBs' dominate tree. 
The old logic will re-iterate and try optimize for each BB.

**Suppose ** we have a big function with 20000 BBs, If we handled the last BB
with fine tuning the dominate tree. We need totally re-iterate and try optimize
the 20000 BBs from the beginning.

The Complex is near N!

And we really encounter somes big tests (> 20000 BBs) that cost more than 30 mins in this pass.


https://reviews.llvm.org/D129352

Files:
  llvm/lib/CodeGen/CodeGenPrepare.cpp


Index: llvm/lib/CodeGen/CodeGenPrepare.cpp
===================================================================
--- llvm/lib/CodeGen/CodeGenPrepare.cpp
+++ llvm/lib/CodeGen/CodeGenPrepare.cpp
@@ -339,6 +339,10 @@
     /// lazily and update it when required.
     std::unique_ptr<DominatorTree> DT;
 
+    /// If there are too many BBs, we need to consider the build time.
+    bool BuildTimeLimit = false;
+    SmallDenseSet<BasicBlock *> VisitedBBs;
+
   public:
     static char ID; // Pass identification, replacement for typeid
 
@@ -474,6 +478,7 @@
   // Clear per function information.
   InsertedInsts.clear();
   PromotedInsts.clear();
+  VisitedBBs.clear();
 
   TM = &getAnalysis<TargetPassConfig>().getTM<TargetMachine>();
   SubtargetInfo = TM->getSubtargetImpl(F);
@@ -545,11 +550,22 @@
   EverMadeChange |=
       SplitIndirectBrCriticalEdges(F, /*IgnoreBlocksWithoutPHI=*/true);
 
+  // Refine Me: We may use better condition to consider the build time.
+  BuildTimeLimit = F.size() > 10000;
+
   bool MadeChange = true;
   while (MadeChange) {
     MadeChange = false;
     DT.reset();
     for (BasicBlock &BB : llvm::make_early_inc_range(F)) {
+      // This is very time consuming when there are big number BBs.
+      // We encounter somes big tests (> 20000 BBs) will cost 30 mins here.
+      // Though some optimizations may affect the dominate relation, usually
+      // split or merge BBs, it just fine tuning in the whole tree.
+      // Most optimized BBs will not be optimized again.
+      if (BuildTimeLimit && VisitedBBs.count(&BB))
+        continue;
+
       bool ModifiedDTOnIteration = false;
       MadeChange |= optimizeBlock(BB, ModifiedDTOnIteration);
 
@@ -8061,6 +8077,9 @@
       return true;
   }
 
+  if (BuildTimeLimit)
+    VisitedBBs.insert(&BB);
+
   bool MadeBitReverse = true;
   while (MadeBitReverse) {
     MadeBitReverse = false;


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D129352.443160.patch
Type: text/x-patch
Size: 1884 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20220708/2a090afb/attachment.bin>


More information about the llvm-commits mailing list