Added RegisterCoalescer to required passes for PBQP.
[oota-llvm.git] / lib / CodeGen / BranchFolding.cpp
index 583009c74a3b6375175801a9eab558478ff0f642..1ab3df28572bfb7222a8db8bebba81ab9736eb9d 100644 (file)
@@ -27,6 +27,7 @@
 #include "llvm/Target/TargetRegisterInfo.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/Debug.h"
+#include "llvm/Support/ErrorHandling.h"
 #include "llvm/ADT/SmallSet.h"
 #include "llvm/ADT/Statistic.h"
 #include "llvm/ADT/STLExtras.h"
@@ -461,7 +462,7 @@ static bool MergeCompare(const std::pair<unsigned,MachineBasicBlock*> &p,
       // _GLIBCXX_DEBUG checks strict weak ordering, which involves comparing
       // an object with itself.
 #ifndef _GLIBCXX_DEBUG
-      assert(0 && "Predecessor appears twice");
+      llvm_unreachable("Predecessor appears twice");
 #endif
       return false;
     }
@@ -849,6 +850,27 @@ bool BranchFolder::CanFallThrough(MachineBasicBlock *CurBB) {
   return CanFallThrough(CurBB, CurUnAnalyzable, TBB, FBB, Cond);
 }
 
+/// RemoveDuplicateSuccessor - make sure block Pred has at most one
+/// successor edge leading to Succ.  This is only called in one place,
+/// but Chris prefers that it be a separate function.
+static void RemoveDuplicateSuccessor(MachineBasicBlock *Pred,
+                                     MachineBasicBlock *Succ) {
+  MachineBasicBlock::succ_iterator SI = Pred->succ_begin();
+  bool found = false;
+  while (SI != Pred->succ_end()) {
+    if (*SI == Succ) {
+      if (!found) {
+        found = true;
+        ++SI;
+      } else {
+        SI = Pred->removeSuccessor(SI);
+      }
+    } else {
+      ++SI;
+    }
+  }
+}
+
 /// IsBetterFallthrough - Return true if it would be clearly better to
 /// fall-through to MBB1 than to fall through into MBB2.  This has to return
 /// a strict ordering, returning true for both (MBB1,MBB2) and (MBB2,MBB1) will
@@ -892,8 +914,11 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
       while (!MBB->pred_empty()) {
         MachineBasicBlock *Pred = *(MBB->pred_end()-1);
         Pred->ReplaceUsesOfBlockWith(MBB, FallThrough);
+        // If this resulted in a predecessor with true and false edges
+        // both going to the fallthrough block, clean up; 
+        // BranchFolding doesn't like this.
+        RemoveDuplicateSuccessor(Pred, FallThrough);
       }
-      
       // If MBB was the target of a jump table, update jump tables to go to the
       // fallthrough instead.
       MBB->getParent()->getJumpTableInfo()->
@@ -1092,6 +1117,21 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
             } else {
               DidChange = true;
               PMBB->ReplaceUsesOfBlockWith(MBB, CurTBB);
+              // If this change resulted in PMBB ending in a conditional
+              // branch where both conditions go to the same destination,
+              // change this to an unconditional branch (and fix the CFG).
+              MachineBasicBlock *NewCurTBB = 0, *NewCurFBB = 0;
+              SmallVector<MachineOperand, 4> NewCurCond;
+              bool NewCurUnAnalyzable = TII->AnalyzeBranch(*PMBB, NewCurTBB,
+                      NewCurFBB, NewCurCond, true);
+              if (!NewCurUnAnalyzable && NewCurTBB && NewCurTBB == NewCurFBB) {
+                TII->RemoveBranch(*PMBB);
+                NewCurCond.clear(); 
+                TII->InsertBranch(*PMBB, NewCurTBB, 0, NewCurCond);
+                MadeChange = true;
+                ++NumBranchOpts;
+                PMBB->CorrectExtraCFGEdges(NewCurTBB, NewCurFBB, false);
+              }
             }
           }