Handle IMPLICIT_DEF with isUndef operand marker, part 2. This patch moves the code to annotate machineoperands to LiveIntervalAnalysis. It also add markers for implicit_def that define physical registers. The rest, is just a lot of details.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@74580 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/LiveIntervalAnalysis.cpp b/lib/CodeGen/LiveIntervalAnalysis.cpp
index b017f91..9339c95 100644
--- a/lib/CodeGen/LiveIntervalAnalysis.cpp
+++ b/lib/CodeGen/LiveIntervalAnalysis.cpp
@@ -23,6 +23,7 @@
 #include "llvm/CodeGen/LiveVariables.h"
 #include "llvm/CodeGen/MachineFrameInfo.h"
 #include "llvm/CodeGen/MachineInstr.h"
+#include "llvm/CodeGen/MachineInstrBuilder.h"
 #include "llvm/CodeGen/MachineLoopInfo.h"
 #include "llvm/CodeGen/MachineRegisterInfo.h"
 #include "llvm/CodeGen/Passes.h"
@@ -33,6 +34,8 @@
 #include "llvm/Target/TargetOptions.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/Debug.h"
+#include "llvm/ADT/DepthFirstIterator.h"
+#include "llvm/ADT/SmallSet.h"
 #include "llvm/ADT/Statistic.h"
 #include "llvm/ADT/STLExtras.h"
 #include <algorithm>
@@ -98,6 +101,93 @@
   }
 }
 
+/// processImplicitDefs - Process IMPLICIT_DEF instructions and make sure
+/// there is one implicit_def for each use. Add isUndef marker to
+/// implicit_def defs and their uses.
+void LiveIntervals::processImplicitDefs() {
+  SmallSet<unsigned, 8> ImpDefRegs;
+  SmallVector<MachineInstr*, 8> ImpDefMIs;
+  MachineBasicBlock *Entry = mf_->begin();
+  SmallPtrSet<MachineBasicBlock*,16> Visited;
+  for (df_ext_iterator<MachineBasicBlock*, SmallPtrSet<MachineBasicBlock*,16> >
+         DFI = df_ext_begin(Entry, Visited), E = df_ext_end(Entry, Visited);
+       DFI != E; ++DFI) {
+    MachineBasicBlock *MBB = *DFI;
+    for (MachineBasicBlock::iterator I = MBB->begin(), E = MBB->end();
+         I != E; ) {
+      MachineInstr *MI = &*I;
+      ++I;
+      if (MI->getOpcode() == TargetInstrInfo::IMPLICIT_DEF) {
+        unsigned Reg = MI->getOperand(0).getReg();
+        MI->getOperand(0).setIsUndef();
+        ImpDefRegs.insert(Reg);
+        ImpDefMIs.push_back(MI);
+        continue;
+      }
+      for (unsigned i = 0; i != MI->getNumOperands(); ++i) {
+        MachineOperand& MO = MI->getOperand(i);
+        if (!MO.isReg() || !MO.isUse())
+          continue;
+        unsigned Reg = MO.getReg();
+        if (!Reg)
+          continue;
+        if (!ImpDefRegs.count(Reg))
+          continue;
+        MO.setIsUndef();
+        if (MO.isKill() || MI->isRegTiedToDefOperand(i))
+          ImpDefRegs.erase(Reg);
+      }
+
+      for (unsigned i = 0; i != MI->getNumOperands(); ++i) {
+        MachineOperand& MO = MI->getOperand(i);
+        if (!MO.isReg() || !MO.isDef())
+          continue;
+        ImpDefRegs.erase(MO.getReg());
+      }
+    }
+
+    // Any outstanding liveout implicit_def's?
+    for (unsigned i = 0, e = ImpDefMIs.size(); i != e; ++i) {
+      MachineInstr *MI = ImpDefMIs[i];
+      unsigned Reg = MI->getOperand(0).getReg();
+      if (TargetRegisterInfo::isPhysicalRegister(Reg))
+        // Physical registers are not liveout (yet).
+        continue;
+      if (!ImpDefRegs.count(Reg))
+        continue;
+      bool HasLocalUse = false;
+      for (MachineRegisterInfo::reg_iterator RI = mri_->reg_begin(Reg),
+             RE = mri_->reg_end(); RI != RE; ) {
+        MachineOperand &RMO = RI.getOperand();
+        MachineInstr *RMI = &*RI;
+        ++RI;
+        if (RMO.isDef()) {
+          // Don't expect another def of the same register.
+          assert(RMI == MI &&
+                 "Register with multiple defs including an implicit_def?");
+          continue;
+        }
+        MachineBasicBlock *RMBB = RMI->getParent();
+        if (RMBB == MBB) {
+          HasLocalUse = true;
+          continue;
+        }
+        const TargetRegisterClass* RC = mri_->getRegClass(Reg);
+        unsigned NewVReg = mri_->createVirtualRegister(RC);
+        BuildMI(*RMBB, RMI, RMI->getDebugLoc(),
+                tii_->get(TargetInstrInfo::IMPLICIT_DEF), NewVReg);
+        RMO.setReg(NewVReg);
+        RMO.setIsUndef();
+        RMO.setIsKill();
+      }
+      if (!HasLocalUse)
+        MI->eraseFromParent();
+    }
+    ImpDefRegs.clear();
+    ImpDefMIs.clear();
+  }
+}
+
 void LiveIntervals::computeNumbering() {
   Index2MiMap OldI2MI = i2miMap_;
   std::vector<IdxMBBPair> OldI2MBB = Idx2MBBMap;
@@ -299,6 +389,7 @@
   lv_ = &getAnalysis<LiveVariables>();
   allocatableRegs_ = tri_->getAllocatableSet(fn);
 
+  processImplicitDefs();
   computeNumbering();
   computeIntervals();
 
@@ -1785,8 +1876,6 @@
         if (MO.isReg() && MO.getReg() == li.reg) {
           MO.setReg(NewVReg);
           MO.setIsUndef();
-          if (MO.isKill())
-            MO.setIsKill(false);
         }
       }
     }
diff --git a/lib/CodeGen/RegAllocLinearScan.cpp b/lib/CodeGen/RegAllocLinearScan.cpp
index 2caa2f9..904b4cb 100644
--- a/lib/CodeGen/RegAllocLinearScan.cpp
+++ b/lib/CodeGen/RegAllocLinearScan.cpp
@@ -545,26 +545,6 @@
     if (!isPhys && vrm_->getPreSplitReg(cur.reg))
       continue;
 
-    // A register defined by an implicit_def can be liveout the def BB and livein
-    // to a use BB. Add it to the livein set of the use BB's.
-    if (!isPhys && cur.empty()) {
-      if (MachineInstr *DefMI = mri_->getVRegDef(cur.reg)) {
-        assert(DefMI->getOpcode() == TargetInstrInfo::IMPLICIT_DEF);
-        MachineBasicBlock *DefMBB = DefMI->getParent();
-        SmallPtrSet<MachineBasicBlock*, 4> Seen;
-        Seen.insert(DefMBB);
-        for (MachineRegisterInfo::reg_iterator ri = mri_->reg_begin(cur.reg),
-               re = mri_->reg_end(); ri != re; ++ri) {
-          MachineInstr *UseMI = &*ri;
-          MachineBasicBlock *UseMBB = UseMI->getParent();
-          if (Seen.insert(UseMBB)) {
-            assert(TargetRegisterInfo::isPhysicalRegister(Reg) &&
-                   "Adding a virtual register to livein set?");
-            UseMBB->addLiveIn(Reg);
-          }
-        }
-      }
-    }
     for (LiveInterval::Ranges::const_iterator I = cur.begin(), E = cur.end();
          I != E; ++I) {
       const LiveRange &LR = *I;
@@ -905,17 +885,6 @@
     DOUT <<  tri_->getName(physReg) << '\n';
     // Note the register is not really in use.
     vrm_->assignVirt2Phys(cur->reg, physReg);
-    // Since the register allocator is allowed to assign this virtual register
-    // physical register that overlaps other live intervals. Mark these
-    // operands as "Undef" which means later passes, e.g. register scavenger
-    // can ignore them.
-    for (MachineRegisterInfo::reg_iterator RI = mri_->reg_begin(cur->reg),
-           RE = mri_->reg_end(); RI != RE; ++RI) {
-      MachineOperand &MO = RI.getOperand();
-      MO.setIsUndef();
-      if (MO.isKill())
-        MO.setIsKill(false);
-    }
     return;
   }
 
diff --git a/lib/CodeGen/RegisterScavenging.cpp b/lib/CodeGen/RegisterScavenging.cpp
index 382741e..58f4284 100644
--- a/lib/CodeGen/RegisterScavenging.cpp
+++ b/lib/CodeGen/RegisterScavenging.cpp
@@ -254,6 +254,8 @@
     unsigned Idx = (i < NumECs)
       ? EarlyClobberMOs[i].second : DefMOs[i-NumECs].second;
     unsigned Reg = MO.getReg();
+    if (MO.isUndef())
+      continue;
 
     // If it's dead upon def, then it is now free.
     if (MO.isDead()) {
@@ -262,7 +264,9 @@
     }
 
     // Skip two-address destination operand.
-    if (MI->isRegTiedToUseOperand(Idx)) {
+    unsigned UseIdx;
+    if (MI->isRegTiedToUseOperand(Idx, &UseIdx) &&
+        !MI->getOperand(UseIdx).isUndef()) {
       assert(isUsed(Reg) && "Using an undefined register!");
       continue;
     }
@@ -316,6 +320,8 @@
       ? *DefMOs[i].first : *EarlyClobberMOs[i-NumDefs].first;
     unsigned Idx = (i < NumECs)
       ? DefMOs[i].second : EarlyClobberMOs[i-NumDefs].second;
+    if (MO.isUndef())
+      continue;
 
     // Skip two-address destination operand.
     if (MI->isRegTiedToUseOperand(Idx))
diff --git a/lib/CodeGen/VirtRegRewriter.cpp b/lib/CodeGen/VirtRegRewriter.cpp
index bbf1e24..be0b016 100644
--- a/lib/CodeGen/VirtRegRewriter.cpp
+++ b/lib/CodeGen/VirtRegRewriter.cpp
@@ -2029,8 +2029,12 @@
         if (!TargetRegisterInfo::isVirtualRegister(VirtReg)) {
           // Check to see if this is a noop copy.  If so, eliminate the
           // instruction before considering the dest reg to be changed.
+          // Also check if it's copying from an "undef", if so, we can't
+          // eliminate this or else the undef marker is lost and it will
+          // confuses the scavenger. This is extremely rare.
           unsigned Src, Dst, SrcSR, DstSR;
-          if (TII->isMoveInstr(MI, Src, Dst, SrcSR, DstSR) && Src == Dst) {
+          if (TII->isMoveInstr(MI, Src, Dst, SrcSR, DstSR) && Src == Dst &&
+              !MI.findRegisterUseOperand(Src)->isUndef()) {
             ++NumDCE;
             DOUT << "Removing now-noop copy: " << MI;
             SmallVector<unsigned, 2> KillRegs;
@@ -2049,7 +2053,7 @@
             Spills.disallowClobberPhysReg(VirtReg);
             goto ProcessNextInst;
           }
-            
+
           // If it's not a no-op copy, it clobbers the value in the destreg.
           Spills.ClobberPhysReg(VirtReg);
           ReusedOperands.markClobbered(VirtReg);