Clear kill flags on the fly when joining intervals.
[oota-llvm.git] / lib / CodeGen / RegisterCoalescer.cpp
index c7dcde6c22581c10ef1d0b4811fbf07f14e9ef76..30997c24bab40af8aeb34eea2449ebef19cfe136 100644 (file)
@@ -1143,6 +1143,10 @@ bool RegisterCoalescer::joinReservedPhysReg(CoalescerPair &CP) {
   // reserved register.  Also skip merging the live ranges, the reserved
   // register live range doesn't need to be accurate as long as all the
   // defs are there.
+
+  // We don't track kills for reserved registers.
+  MRI->clearKillFlags(CP.getSrcReg());
+
   return true;
 }
 
@@ -1310,13 +1314,13 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
 
     // DstReg is known to be a register in the LHS interval.  If the src is
     // from the RHS interval, we can use its value #.
-    if (!CP.isCoalescable(MI) &&
-        !RegistersDefinedFromSameValue(*LIS, *TRI, CP, VNI, OtherVNI,
-                                       DupCopies))
+    if (CP.isCoalescable(MI))
+      DeadCopies.push_back(MI);
+    else if (!RegistersDefinedFromSameValue(*LIS, *TRI, CP, VNI, OtherVNI,
+                                            DupCopies))
       continue;
 
     LHSValsDefinedFromRHS[VNI] = OtherVNI;
-    DeadCopies.push_back(MI);
   }
 
   // Loop over the value numbers of the RHS, seeing if any are defined from
@@ -1339,13 +1343,13 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
 
     // DstReg is known to be a register in the RHS interval.  If the src is
     // from the LHS interval, we can use its value #.
-    if (!CP.isCoalescable(MI) &&
-        !RegistersDefinedFromSameValue(*LIS, *TRI, CP, VNI, OtherVNI,
-                                       DupCopies))
+    if (CP.isCoalescable(MI))
+      DeadCopies.push_back(MI);
+    else if (!RegistersDefinedFromSameValue(*LIS, *TRI, CP, VNI, OtherVNI,
+                                            DupCopies))
         continue;
 
     RHSValsDefinedFromLHS[VNI] = OtherVNI;
-    DeadCopies.push_back(MI);
   }
 
   LHSValNoAssignments.resize(LHS.getNumValNums(), -1);
@@ -1387,6 +1391,10 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
   LiveInterval::const_iterator J = RHS.begin();
   LiveInterval::const_iterator JE = RHS.end();
 
+  // Collect interval end points that will no longer be kills.
+  SmallVector<MachineInstr*, 8> LHSOldKills;
+  SmallVector<MachineInstr*, 8> RHSOldKills;
+
   // Skip ahead until the first place of potential sharing.
   if (I != IE && J != JE) {
     if (I->start < J->start) {
@@ -1407,6 +1415,14 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
       if (LHSValNoAssignments[I->valno->id] !=
           RHSValNoAssignments[J->valno->id])
         return false;
+
+      // Extended live ranges should no longer be killed.
+      if (!I->end.isBlock() && I->end < J->end)
+        if (MachineInstr *MI = LIS->getInstructionFromIndex(I->end))
+          LHSOldKills.push_back(MI);
+      if (!J->end.isBlock() && J->end < I->end)
+        if (MachineInstr *MI = LIS->getInstructionFromIndex(J->end))
+          RHSOldKills.push_back(MI);
     }
 
     if (I->end < J->end)
@@ -1433,6 +1449,12 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
       NewVNInfo[RHSValID]->setHasPHIKill(true);
   }
 
+  // Clear kill flags where live ranges are extended.
+  while (!LHSOldKills.empty())
+    LHSOldKills.pop_back_val()->clearRegisterKills(LHS.reg, TRI);
+  while (!RHSOldKills.empty())
+    RHSOldKills.pop_back_val()->clearRegisterKills(RHS.reg, TRI);
+
   if (LHSValNoAssignments.empty())
     LHSValNoAssignments.push_back(-1);
   if (RHSValNoAssignments.empty())
@@ -1441,10 +1463,10 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
   // Now erase all the redundant copies.
   for (unsigned i = 0, e = DeadCopies.size(); i != e; ++i) {
     MachineInstr *MI = DeadCopies[i];
-    DEBUG(dbgs() << "\t\terased:\t" << LIS->getInstructionIndex(MI)
-                 << '\t' << *MI);
     if (!ErasedInstrs.insert(MI))
       continue;
+    DEBUG(dbgs() << "\t\terased:\t" << LIS->getInstructionIndex(MI)
+                 << '\t' << *MI);
     LIS->RemoveMachineInstrFromMaps(MI);
     MI->eraseFromParent();
   }
@@ -1453,6 +1475,8 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
   for (SmallVector<MachineInstr*, 8>::iterator I = DupCopies.begin(),
          E = DupCopies.end(); I != E; ++I) {
     MachineInstr *MI = *I;
+    if (!ErasedInstrs.insert(MI))
+      continue;
 
     // We have pretended that the assignment to B in
     // A = X
@@ -1462,8 +1486,6 @@ bool RegisterCoalescer::joinIntervals(CoalescerPair &CP) {
     // A = X
     unsigned Src = MI->getOperand(1).getReg();
     SourceRegisters.push_back(Src);
-    if (!ErasedInstrs.insert(MI))
-      continue;
     LIS->RemoveMachineInstrFromMaps(MI);
     MI->eraseFromParent();
   }
@@ -1624,42 +1646,6 @@ bool RegisterCoalescer::runOnMachineFunction(MachineFunction &fn) {
       });
   }
 
-  // Perform a final pass over the instructions and compute spill weights
-  // and remove identity moves.
-  SmallVector<unsigned, 4> DeadDefs;
-  for (MachineFunction::iterator mbbi = MF->begin(), mbbe = MF->end();
-       mbbi != mbbe; ++mbbi) {
-    MachineBasicBlock* mbb = mbbi;
-    for (MachineBasicBlock::iterator mii = mbb->begin(), mie = mbb->end();
-         mii != mie; ) {
-      MachineInstr *MI = mii;
-
-      ++mii;
-
-      // Check for now unnecessary kill flags.
-      if (LIS->isNotInMIMap(MI)) continue;
-      SlotIndex DefIdx = LIS->getInstructionIndex(MI).getRegSlot();
-      for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
-        MachineOperand &MO = MI->getOperand(i);
-        if (!MO.isReg() || !MO.isKill()) continue;
-        unsigned reg = MO.getReg();
-        if (!reg || !LIS->hasInterval(reg)) continue;
-        if (!LIS->getInterval(reg).killedAt(DefIdx)) {
-          MO.setIsKill(false);
-          continue;
-        }
-        // When leaving a kill flag on a physreg, check if any subregs should
-        // remain alive.
-        if (!TargetRegisterInfo::isPhysicalRegister(reg))
-          continue;
-        for (const uint16_t *SR = TRI->getSubRegisters(reg);
-             unsigned S = *SR; ++SR)
-          if (LIS->hasInterval(S) && LIS->getInterval(S).liveAt(DefIdx))
-            MI->addRegisterDefined(S, TRI);
-      }
-    }
-  }
-
   // After deleting a lot of copies, register classes may be less constrained.
   // Removing sub-register operands may allow GR32_ABCD -> GR32 and DPR_VFP2 ->
   // DPR inflation.