Change TargetInstrInfo::isMoveInstr to return source and destination sub-register indices as well.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@62600 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/LiveIntervalAnalysis.cpp b/lib/CodeGen/LiveIntervalAnalysis.cpp
index 2259589..8cd82a6 100644
--- a/lib/CodeGen/LiveIntervalAnalysis.cpp
+++ b/lib/CodeGen/LiveIntervalAnalysis.cpp
@@ -298,8 +298,8 @@
       if (index == end) break;
 
       MachineInstr *MI = getInstructionFromIndex(index);
-      unsigned SrcReg, DstReg;
-      if (tii_->isMoveInstr(*MI, SrcReg, DstReg))
+      unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+      if (tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubReg, DstSubReg))
         if (SrcReg == li.reg || DstReg == li.reg)
           continue;
       for (unsigned i = 0; i != MI->getNumOperands(); ++i) {
@@ -396,10 +396,10 @@
       defIndex = getUseIndex(MIIdx);
     VNInfo *ValNo;
     MachineInstr *CopyMI = NULL;
-    unsigned SrcReg, DstReg;
+    unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
     if (mi->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG ||
         mi->getOpcode() == TargetInstrInfo::INSERT_SUBREG ||
-        tii_->isMoveInstr(*mi, SrcReg, DstReg))
+        tii_->isMoveInstr(*mi, SrcReg, DstReg, SrcSubReg, DstSubReg))
       CopyMI = mi;
     // Earlyclobbers move back one.
     ValNo = interval.getNextValue(defIndex, CopyMI, VNInfoAllocator);
@@ -551,10 +551,10 @@
       
       VNInfo *ValNo;
       MachineInstr *CopyMI = NULL;
-      unsigned SrcReg, DstReg;
+      unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
       if (mi->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG ||
           mi->getOpcode() == TargetInstrInfo::INSERT_SUBREG ||
-          tii_->isMoveInstr(*mi, SrcReg, DstReg))
+          tii_->isMoveInstr(*mi, SrcReg, DstReg, SrcSubReg, DstSubReg))
         CopyMI = mi;
       ValNo = interval.getNextValue(defIndex, CopyMI, VNInfoAllocator);
       
@@ -653,10 +653,10 @@
                              getOrCreateInterval(MO.getReg()));
   else if (allocatableRegs_[MO.getReg()]) {
     MachineInstr *CopyMI = NULL;
-    unsigned SrcReg, DstReg;
+    unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
     if (MI->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG ||
         MI->getOpcode() == TargetInstrInfo::INSERT_SUBREG ||
-        tii_->isMoveInstr(*MI, SrcReg, DstReg))
+        tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubReg, DstSubReg))
       CopyMI = MI;
     handlePhysicalRegisterDef(MBB, MI, MIIdx, MO, 
                               getOrCreateInterval(MO.getReg()), CopyMI);
@@ -844,8 +844,8 @@
   } else if (VNI->copy->getOpcode() == TargetInstrInfo::INSERT_SUBREG)
     return VNI->copy->getOperand(2).getReg();
 
-  unsigned SrcReg, DstReg;
-  if (tii_->isMoveInstr(*VNI->copy, SrcReg, DstReg))
+  unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+  if (tii_->isMoveInstr(*VNI->copy, SrcReg, DstReg, SrcSubReg, DstSubReg))
     return SrcReg;
   assert(0 && "Unrecognized copy instruction!");
   return 0;
diff --git a/lib/CodeGen/PreAllocSplitting.cpp b/lib/CodeGen/PreAllocSplitting.cpp
index 2f49e25..6b37637 100644
--- a/lib/CodeGen/PreAllocSplitting.cpp
+++ b/lib/CodeGen/PreAllocSplitting.cpp
@@ -846,9 +846,9 @@
     VNInfo* NewVN = LI->getNextValue(DefIdx, 0, Alloc);
     
     // If the def is a move, set the copy field.
-    unsigned source, dest;
-    if (TII->isMoveInstr(*DI, source, dest))
-      if (dest == LI->reg)
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (TII->isMoveInstr(*DI, SrcReg, DstReg, SrcSubIdx, DstSubIdx))
+      if (DstReg == LI->reg)
         NewVN->copy = &*DI;
     
     NewVNs[&*DI] = NewVN;
diff --git a/lib/CodeGen/RegAllocBigBlock.cpp b/lib/CodeGen/RegAllocBigBlock.cpp
index 73845db..584aa7c 100644
--- a/lib/CodeGen/RegAllocBigBlock.cpp
+++ b/lib/CodeGen/RegAllocBigBlock.cpp
@@ -823,8 +823,9 @@
     }
     
     // Finally, if this is a noop copy instruction, zap it.
-    unsigned SrcReg, DstReg;
-    if (TII.isMoveInstr(*MI, SrcReg, DstReg) && SrcReg == DstReg)
+    unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+    if (TII.isMoveInstr(*MI, SrcReg, DstReg, SrcSubReg, DstSubReg) &&
+        SrcReg == DstReg)
       MBB.erase(MI);
   }
 
diff --git a/lib/CodeGen/RegAllocLinearScan.cpp b/lib/CodeGen/RegAllocLinearScan.cpp
index 96f8ab4..a944461 100644
--- a/lib/CodeGen/RegAllocLinearScan.cpp
+++ b/lib/CodeGen/RegAllocLinearScan.cpp
@@ -253,8 +253,9 @@
   if (!vni->def || vni->def == ~1U || vni->def == ~0U)
     return Reg;
   MachineInstr *CopyMI = li_->getInstructionFromIndex(vni->def);
-  unsigned SrcReg, DstReg;
-  if (!CopyMI || !tii_->isMoveInstr(*CopyMI, SrcReg, DstReg))
+  unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+  if (!CopyMI ||
+      !tii_->isMoveInstr(*CopyMI, SrcReg, DstReg, SrcSubReg, DstSubReg))
     return Reg;
   if (TargetRegisterInfo::isVirtualRegister(SrcReg)) {
     if (!vrm_->isAssignedReg(SrcReg))
@@ -695,8 +696,9 @@
     VNInfo *vni = cur->begin()->valno;
     if (vni->def && vni->def != ~1U && vni->def != ~0U) {
       MachineInstr *CopyMI = li_->getInstructionFromIndex(vni->def);
-      unsigned SrcReg, DstReg;
-      if (CopyMI && tii_->isMoveInstr(*CopyMI, SrcReg, DstReg)) {
+      unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+      if (CopyMI &&
+          tii_->isMoveInstr(*CopyMI, SrcReg, DstReg, SrcSubReg, DstSubReg)) {
         unsigned Reg = 0;
         if (TargetRegisterInfo::isPhysicalRegister(SrcReg))
           Reg = SrcReg;
diff --git a/lib/CodeGen/RegAllocLocal.cpp b/lib/CodeGen/RegAllocLocal.cpp
index bf4e205..acd3dde 100644
--- a/lib/CodeGen/RegAllocLocal.cpp
+++ b/lib/CodeGen/RegAllocLocal.cpp
@@ -960,8 +960,9 @@
     }
     
     // Finally, if this is a noop copy instruction, zap it.
-    unsigned SrcReg, DstReg;
-    if (TII->isMoveInstr(*MI, SrcReg, DstReg) && SrcReg == DstReg)
+    unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
+    if (TII->isMoveInstr(*MI, SrcReg, DstReg, SrcSubReg, DstSubReg) &&
+        SrcReg == DstReg)
       MBB.erase(MI);
   }
 
diff --git a/lib/CodeGen/RegAllocPBQP.cpp b/lib/CodeGen/RegAllocPBQP.cpp
index 40f7570..dfee8cf9b 100644
--- a/lib/CodeGen/RegAllocPBQP.cpp
+++ b/lib/CodeGen/RegAllocPBQP.cpp
@@ -359,10 +359,10 @@
          iItr != iEnd; ++iItr) {
 
       const MachineInstr *instr = &*iItr;
-      unsigned srcReg, dstReg;
+      unsigned srcReg, dstReg, srcSubReg, dstSubReg;
 
       // If this isn't a copy then continue to the next instruction.
-      if (!tii->isMoveInstr(*instr, srcReg, dstReg))
+      if (!tii->isMoveInstr(*instr, srcReg, dstReg, srcSubReg, dstSubReg))
         continue;
 
       // If the registers are already the same our job is nice and easy.
diff --git a/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
index 547cd8d..ca0cd6e 100644
--- a/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
+++ b/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
@@ -189,9 +189,9 @@
   // don't coalesce. Also, only coalesce away a virtual register to virtual
   // register copy.
   bool Coalesced = false;
-  unsigned SrcReg, DstReg;
+  unsigned SrcReg, DstReg, SrcSubReg, DstSubReg;
   if (NumUses == 1 &&
-      TII.isMoveInstr(*UseMI, SrcReg, DstReg) &&
+      TII.isMoveInstr(*UseMI, SrcReg, DstReg, SrcSubReg, DstSubReg) &&
       TargetRegisterInfo::isVirtualRegister(DstReg)) {
     VirtReg = DstReg;
     Coalesced = true;
diff --git a/lib/CodeGen/SimpleRegisterCoalescing.cpp b/lib/CodeGen/SimpleRegisterCoalescing.cpp
index 09b610c..637d74b 100644
--- a/lib/CodeGen/SimpleRegisterCoalescing.cpp
+++ b/lib/CodeGen/SimpleRegisterCoalescing.cpp
@@ -386,8 +386,8 @@
       else
         BKills.push_back(li_->getUseIndex(UseIdx)+1);
     }
-    unsigned SrcReg, DstReg;
-    if (!tii_->isMoveInstr(*UseMI, SrcReg, DstReg))
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (!tii_->isMoveInstr(*UseMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx))
       continue;
     if (DstReg == IntB.reg) {
       // This copy will become a noop. If it's defining a new val#,
@@ -563,8 +563,9 @@
       if (OldSubIdx)
           UseDstReg = tri_->getSubReg(DstReg, OldSubIdx);
 
-      unsigned CopySrcReg, CopyDstReg;
-      if (tii_->isMoveInstr(*UseMI, CopySrcReg, CopyDstReg) &&
+      unsigned CopySrcReg, CopyDstReg, CopySrcSubIdx, CopyDstSubIdx;
+      if (tii_->isMoveInstr(*UseMI, CopySrcReg, CopyDstReg,
+                            CopySrcSubIdx, CopyDstSubIdx) &&
           CopySrcReg != CopyDstReg &&
           CopySrcReg == SrcReg && CopyDstReg != UseDstReg) {
         // If the use is a copy and it won't be coalesced away, and its source
@@ -595,9 +596,10 @@
     // After updating the operand, check if the machine instruction has
     // become a copy. If so, update its val# information.
     const TargetInstrDesc &TID = UseMI->getDesc();
-    unsigned CopySrcReg, CopyDstReg;
+    unsigned CopySrcReg, CopyDstReg, CopySrcSubIdx, CopyDstSubIdx;
     if (TID.getNumDefs() == 1 && TID.getNumOperands() > 2 &&
-        tii_->isMoveInstr(*UseMI, CopySrcReg, CopyDstReg) &&
+        tii_->isMoveInstr(*UseMI, CopySrcReg, CopyDstReg,
+                          CopySrcSubIdx, CopyDstSubIdx) &&
         CopySrcReg != CopyDstReg &&
         (TargetRegisterInfo::isVirtualRegister(CopyDstReg) ||
          allocatableRegs_[CopyDstReg])) {
@@ -818,8 +820,8 @@
     // of last use.
     LastUse->setIsKill();
     removeRange(li, li_->getDefIndex(LastUseIdx), LR->end, li_, tri_);
-    unsigned SrcReg, DstReg;
-    if (tii_->isMoveInstr(*LastUseMI, SrcReg, DstReg) &&
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (tii_->isMoveInstr(*LastUseMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx) &&
         DstReg == li.reg) {
       // Last use is itself an identity code.
       int DeadIdx = LastUseMI->findRegisterDefOperandIdx(li.reg, false, tri_);
@@ -873,8 +875,8 @@
     if (ULR == li.end() || ULR->valno != LR->valno)
       continue;
     // If the use is not a use, then it's not safe to coalesce the move.
-    unsigned SrcReg, DstReg;
-    if (!tii_->isMoveInstr(*UseMI, SrcReg, DstReg)) {
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (!tii_->isMoveInstr(*UseMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx)) {
       if (UseMI->getOpcode() == TargetInstrInfo::INSERT_SUBREG &&
           UseMI->getOperand(1).getReg() == li.reg)
         continue;
@@ -911,8 +913,9 @@
     if (ULR == li.end() || ULR->valno != VNI)
       continue;
     // If the use is a copy, turn it into an identity copy.
-    unsigned SrcReg, DstReg;
-    if (tii_->isMoveInstr(*MI, SrcReg, DstReg) && SrcReg == li.reg) {
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubIdx, DstSubIdx) &&
+        SrcReg == li.reg) {
       // Each use MI may have multiple uses of this register. Change them all.
       for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
         MachineOperand &MO = MI->getOperand(i);
@@ -1123,8 +1126,7 @@
 
   DOUT << li_->getInstructionIndex(CopyMI) << '\t' << *CopyMI;
 
-  unsigned SrcReg;
-  unsigned DstReg;
+  unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
   bool isExtSubReg = CopyMI->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG;
   bool isInsSubReg = CopyMI->getOpcode() == TargetInstrInfo::INSERT_SUBREG;
   unsigned SubIdx = 0;
@@ -1139,7 +1141,7 @@
     }
     DstReg = CopyMI->getOperand(0).getReg();
     SrcReg = CopyMI->getOperand(2).getReg();
-  } else if (!tii_->isMoveInstr(*CopyMI, SrcReg, DstReg)) {
+  } else if (!tii_->isMoveInstr(*CopyMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx)){
     assert(0 && "Unrecognized copy instruction!");
     return false;
   }
@@ -1428,10 +1430,11 @@
       if (!vni->def || vni->def == ~1U || vni->def == ~0U)
         continue;
       MachineInstr *CopyMI = li_->getInstructionFromIndex(vni->def);
-      unsigned NewSrcReg, NewDstReg;
+      unsigned NewSrcReg, NewDstReg, NewSrcSubIdx, NewDstSubIdx;
       if (CopyMI &&
           JoinedCopies.count(CopyMI) == 0 &&
-          tii_->isMoveInstr(*CopyMI, NewSrcReg, NewDstReg)) {
+          tii_->isMoveInstr(*CopyMI, NewSrcReg, NewDstReg,
+                            NewSrcSubIdx, NewDstSubIdx)) {
         unsigned LoopDepth = loopInfo->getLoopDepth(CopyMBB);
         JoinQueue->push(CopyRec(CopyMI, LoopDepth,
                                 isBackEdgeCopy(CopyMI, DstReg)));
@@ -1570,8 +1573,9 @@
     // It's a sub-register live interval, we may not have precise information.
     // Re-compute it.
     MachineInstr *DefMI = li_->getInstructionFromIndex(LR->start);
-    unsigned SrcReg, DstReg;
-    if (DefMI && tii_->isMoveInstr(*DefMI, SrcReg, DstReg) &&
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (DefMI &&
+        tii_->isMoveInstr(*DefMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx) &&
         DstReg == li.reg && SrcReg == Reg) {
       // Cache computed info.
       LR->valno->def  = LR->start;
@@ -2070,14 +2074,14 @@
     MachineInstr *Inst = MII++;
     
     // If this isn't a copy nor a extract_subreg, we can't join intervals.
-    unsigned SrcReg, DstReg;
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
     if (Inst->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG) {
       DstReg = Inst->getOperand(0).getReg();
       SrcReg = Inst->getOperand(1).getReg();
     } else if (Inst->getOpcode() == TargetInstrInfo::INSERT_SUBREG) {
       DstReg = Inst->getOperand(0).getReg();
       SrcReg = Inst->getOperand(2).getReg();
-    } else if (!tii_->isMoveInstr(*Inst, SrcReg, DstReg))
+    } else if (!tii_->isMoveInstr(*Inst, SrcReg, DstReg, SrcSubIdx, DstSubIdx))
       continue;
 
     bool SrcIsPhys = TargetRegisterInfo::isPhysicalRegister(SrcReg);
@@ -2243,8 +2247,9 @@
            E = mri_->use_end(); I != E; ++I) {
       MachineOperand &Use = I.getOperand();
       MachineInstr *UseMI = Use.getParent();
-      unsigned SrcReg, DstReg;
-      if (tii_->isMoveInstr(*UseMI, SrcReg, DstReg) && SrcReg == DstReg)
+      unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+      if (tii_->isMoveInstr(*UseMI, SrcReg, DstReg, SrcSubIdx, DstSubIdx) &&
+          SrcReg == DstReg)
         // Ignore identity copies.
         continue;
       unsigned Idx = li_->getInstructionIndex(UseMI);
@@ -2269,8 +2274,9 @@
       return NULL;
 
     // Ignore identity copies.
-    unsigned SrcReg, DstReg;
-    if (!(tii_->isMoveInstr(*MI, SrcReg, DstReg) && SrcReg == DstReg))
+    unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
+    if (!(tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubIdx, DstSubIdx) &&
+          SrcReg == DstReg))
       for (unsigned i = 0, NumOps = MI->getNumOperands(); i != NumOps; ++i) {
         MachineOperand &Use = MI->getOperand(i);
         if (Use.isReg() && Use.isUse() && Use.getReg() &&
@@ -2389,10 +2395,10 @@
     for (MachineBasicBlock::iterator mii = mbb->begin(), mie = mbb->end();
          mii != mie; ) {
       MachineInstr *MI = mii;
-      unsigned SrcReg, DstReg;
+      unsigned SrcReg, DstReg, SrcSubIdx, DstSubIdx;
       if (JoinedCopies.count(MI)) {
         // Delete all coalesced copies.
-        if (!tii_->isMoveInstr(*MI, SrcReg, DstReg)) {
+        if (!tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubIdx, DstSubIdx)) {
           assert((MI->getOpcode() == TargetInstrInfo::EXTRACT_SUBREG ||
                   MI->getOpcode() == TargetInstrInfo::INSERT_SUBREG) &&
                  "Unrecognized copy instruction");
@@ -2441,7 +2447,7 @@
       }
 
       // If the move will be an identity move delete it
-      bool isMove = tii_->isMoveInstr(*MI, SrcReg, DstReg);
+      bool isMove= tii_->isMoveInstr(*MI, SrcReg, DstReg, SrcSubIdx, DstSubIdx);
       if (isMove && SrcReg == DstReg) {
         if (li_->hasInterval(SrcReg)) {
           LiveInterval &RegInt = li_->getInterval(SrcReg);
diff --git a/lib/CodeGen/VirtRegMap.cpp b/lib/CodeGen/VirtRegMap.cpp
index dab0215..b35fc2c 100644
--- a/lib/CodeGen/VirtRegMap.cpp
+++ b/lib/CodeGen/VirtRegMap.cpp
@@ -1753,8 +1753,8 @@
       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.
-        unsigned Src, Dst;
-        if (TII->isMoveInstr(MI, Src, Dst) && Src == Dst) {
+        unsigned Src, Dst, SrcSR, DstSR;
+        if (TII->isMoveInstr(MI, Src, Dst, SrcSR, DstSR) && Src == Dst) {
           ++NumDCE;
           DOUT << "Removing now-noop copy: " << MI;
           SmallVector<unsigned, 2> KillRegs;
@@ -1840,8 +1840,8 @@
         // Check to see if this is a noop copy.  If so, eliminate the
         // instruction before considering the dest reg to be changed.
         {
-          unsigned Src, Dst;
-          if (TII->isMoveInstr(MI, Src, Dst) && Src == Dst) {
+          unsigned Src, Dst, SrcSR, DstSR;
+          if (TII->isMoveInstr(MI, Src, Dst, SrcSR, DstSR) && Src == Dst) {
             ++NumDCE;
             DOUT << "Removing now-noop copy: " << MI;
             InvalidateKills(MI, RegKills, KillOps);