[PATCH] D23824: [ADCE] Add handling of PHI nodes when removing control flow

David Callahan via llvm-commits llvm-commits at lists.llvm.org
Fri Sep 9 06:58:32 PDT 2016


david2050 updated this revision to Diff 70829.
david2050 added a comment.

Introduce CFLive field to mark blocks whose control dependence sources should be live; use this for PHI predecessors and blocks with live operations


https://reviews.llvm.org/D23824

Files:
  lib/Transforms/Scalar/ADCE.cpp

Index: lib/Transforms/Scalar/ADCE.cpp
===================================================================
--- lib/Transforms/Scalar/ADCE.cpp
+++ lib/Transforms/Scalar/ADCE.cpp
@@ -58,6 +58,10 @@
   bool Live = false;
   /// True when this block ends in an unconditional branch.
   bool UnconditionalBranch = false;
+  /// True when this block is known to have live PHI nodes.
+  bool HasLivePhiNodes = false;
+  /// Control dependence sources need to be live for this block.
+  bool CFLive = false;
 
   /// Quick access to the LiveInfo for the terminator,
   /// holds the value &InstInfo[Terminator]
@@ -109,6 +113,9 @@
   void markLiveInstructions();
   /// Mark an instruction as live.
   void markLive(Instruction *I);
+  
+  /// Mark terminators of control predecessors of a PHI node live.
+  void markPhiLive(PHINode *PN);
 
   /// Record the Debug Scopes which surround live debug information.
   void collectLiveScopes(const DILocalScope &LS);
@@ -269,15 +276,18 @@
     // where we need to mark the inputs as live.
     while (!Worklist.empty()) {
       Instruction *LiveInst = Worklist.pop_back_val();
+      DEBUG(dbgs() << "work live: "; LiveInst->dump(););
 
       // Collect the live debug info scopes attached to this instruction.
       if (const DILocation *DL = LiveInst->getDebugLoc())
         collectLiveScopes(*DL);
 
-      DEBUG(dbgs() << "work live: "; LiveInst->dump(););
       for (Use &OI : LiveInst->operands())
         if (Instruction *Inst = dyn_cast<Instruction>(OI))
           markLive(Inst);
+      
+      if (auto *PN = dyn_cast<PHINode>(LiveInst))
+        markPhiLive(PN);
     }
     markLiveBranchesFromControlDependences();
 
@@ -315,7 +325,10 @@
 
   DEBUG(dbgs() << "mark block live: " << BBInfo.BB->getName() << '\n');
   BBInfo.Live = true;
-  NewLiveBlocks.insert(BBInfo.BB);
+  if (!BBInfo.CFLive) {
+    BBInfo.CFLive = true;
+    NewLiveBlocks.insert(BBInfo.BB);
+  }
 
   // Mark unconditional branches at the end of live
   // blocks as live since there is no work to do for them later
@@ -348,6 +361,25 @@
     collectLiveScopes(*IA);
 }
 
+void AggressiveDeadCodeElimination::markPhiLive(llvm::PHINode *PN) {
+  auto &Info = BlockInfo[PN->getParent()];
+  // Only need to check this once per block.
+  if(Info.HasLivePhiNodes)
+    return;
+  Info.HasLivePhiNodes = true;
+  
+  // If a predecessor block is not live, mark it as control-flow live
+  // which will trigger marking live branches upon which
+  // that block is control dependent.
+  for (auto *PredBB : predecessors(Info.BB)) {
+    auto &Info = BlockInfo[PredBB];
+    if (!Info.CFLive) {
+      Info.CFLive = true;
+      NewLiveBlocks.insert(PredBB);
+    }
+  }
+}
+
 void AggressiveDeadCodeElimination::markLiveBranchesFromControlDependences() {
 
   if (BlocksWithDeadTerminators.empty())
@@ -382,6 +414,11 @@
   }
 }
 
+//===----------------------------------------------------------------------===//
+//
+//  Routines to update the CFG and SSA information before removing dead code.
+//
+//===----------------------------------------------------------------------===//
 bool AggressiveDeadCodeElimination::removeDeadInstructions() {
 
   // The inverse of the live set is the dead set.  These are those instructions


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D23824.70829.patch
Type: text/x-patch
Size: 3247 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20160909/ee04d754/attachment.bin>


More information about the llvm-commits mailing list