[llvm-commits] CVS: llvm/lib/CodeGen/LiveIntervalAnalysis.cpp

Evan Cheng evan.cheng at apple.com
Mon May 14 14:10:29 PDT 2007



Changes in directory llvm/lib/CodeGen:

LiveIntervalAnalysis.cpp updated: 1.243 -> 1.244
---
Log message:

Fix for PR1406: http://llvm.org/PR1406 :

v1 =
r2 = move v1
   = op r2<kill>
...
r2 = move v1
   = op r2<kill>

Clear the first r2 kill if v1 and r2 are joined.

---
Diffs of the changes:  (+35 -2)

 LiveIntervalAnalysis.cpp |   37 +++++++++++++++++++++++++++++++++++--
 1 files changed, 35 insertions(+), 2 deletions(-)


Index: llvm/lib/CodeGen/LiveIntervalAnalysis.cpp
diff -u llvm/lib/CodeGen/LiveIntervalAnalysis.cpp:1.243 llvm/lib/CodeGen/LiveIntervalAnalysis.cpp:1.244
--- llvm/lib/CodeGen/LiveIntervalAnalysis.cpp:1.243	Wed May  2 20:11:53 2007
+++ llvm/lib/CodeGen/LiveIntervalAnalysis.cpp	Mon May 14 16:10:05 2007
@@ -977,7 +977,7 @@
       isDead = false;
     } else {
       MachineOperand *MOU;
-      MachineInstr *LastUse= lastRegisterUse(repSrcReg, SrcStart, CopyIdx, MOU);
+      MachineInstr *LastUse= lastRegisterUse(SrcStart, CopyIdx, repSrcReg, MOU);
       if (LastUse) {
         // Shorten the liveinterval to the end of last use.
         MOU->setIsKill();
@@ -1072,6 +1072,11 @@
   // we have to update any aliased register's live ranges to indicate that they
   // have clobbered values for this range.
   if (MRegisterInfo::isPhysicalRegister(repDstReg)) {
+    // Unset unnecessary kills.
+    for (LiveInterval::Ranges::const_iterator I = SrcInt.begin(),
+           E = SrcInt.end(); I != E; ++I)
+      unsetRegisterKills(I->start, I->end, repDstReg);
+
     // Update the liveintervals of sub-registers.
     for (const unsigned *AS = mri_->getSubRegisters(repDstReg); *AS; ++AS)
         getInterval(*AS).MergeInClobberRanges(SrcInt);
@@ -1632,7 +1637,7 @@
 /// cycles Start and End. It also returns the use operand by reference. It
 /// returns NULL if there are no uses.
 MachineInstr *
-LiveIntervals::lastRegisterUse(unsigned Reg, unsigned Start, unsigned End,
+LiveIntervals::lastRegisterUse(unsigned Start, unsigned End, unsigned Reg,
                                MachineOperand *&MOU) {
   int e = (End-1) / InstrSlots::NUM * InstrSlots::NUM;
   int s = Start;
@@ -1685,6 +1690,34 @@
   }
 }
 
+/// unsetRegisterKills - Unset IsKill property of all uses of specific register
+/// between cycles Start and End.
+void LiveIntervals::unsetRegisterKills(unsigned Start, unsigned End,
+                                       unsigned Reg) {
+  int e = (End-1) / InstrSlots::NUM * InstrSlots::NUM;
+  int s = Start;
+  while (e >= s) {
+    // Skip deleted instructions
+    MachineInstr *MI = getInstructionFromIndex(e);
+    while ((e - InstrSlots::NUM) >= s && !MI) {
+      e -= InstrSlots::NUM;
+      MI = getInstructionFromIndex(e);
+    }
+    if (e < s || MI == NULL)
+      return;
+
+    for (unsigned i = 0, NumOps = MI->getNumOperands(); i != NumOps; ++i) {
+      MachineOperand &MO = MI->getOperand(i);
+      if (MO.isReg() && MO.isUse() && MO.isKill() && MO.getReg() &&
+          mri_->regsOverlap(rep(MO.getReg()), Reg)) {
+        MO.unsetIsKill();
+      }
+    }
+
+    e -= InstrSlots::NUM;
+  }
+}
+
 /// hasRegisterDef - True if the instruction defines the specific register.
 ///
 bool LiveIntervals::hasRegisterDef(MachineInstr *MI, unsigned Reg) {






More information about the llvm-commits mailing list