Correctly compute live variable information for physical registers
authorAlkis Evlogimenos <alkis@evlogimenos.com>
Tue, 13 Jan 2004 06:24:30 +0000 (06:24 +0000)
committerAlkis Evlogimenos <alkis@evlogimenos.com>
Tue, 13 Jan 2004 06:24:30 +0000 (06:24 +0000)
when an implicitely defined register is later used by an alias. For example:

         call foo
         %reg1024 = mov %AL

The call implicitely defines EAX but only AL is used. Before this fix
no information was available on AL. Now EAX and all its aliases except
AL get defined and die at the call instruction whereas AL lives to be
killed by the assignment.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@10813 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/LiveIntervalAnalysis.cpp
lib/CodeGen/LiveVariables.cpp
lib/CodeGen/RegAllocLocal.cpp

index fe47a3661d8e2838d8c1fdf4993684defb47b83a..f8c83f18ead27f56550b4b46be55fdc5d7462c47 100644 (file)
@@ -261,6 +261,8 @@ void LiveIntervals::handleRegisterDef(MachineBasicBlock* mbb,
     if (reg < MRegisterInfo::FirstVirtualRegister) {
         if (allocatableRegisters_[reg]) {
             handlePhysicalRegisterDef(mbb, mi, reg);
+            for (const unsigned* as = mri_->getAliasSet(reg); *as; ++as)
+                handlePhysicalRegisterDef(mbb, mi, *as);
         }
     }
     else {
@@ -300,10 +302,8 @@ void LiveIntervals::computeIntervals()
                   instr->print(std::cerr, *tm_););
 
             // handle implicit defs
-            for (const unsigned* id = tid.ImplicitDefs; *id; ++id) {
-                unsigned physReg = *id;
-                handlePhysicalRegisterDef(mbb, mi, physReg);
-            }
+            for (const unsigned* id = tid.ImplicitDefs; *id; ++id)
+                handleRegisterDef(mbb, mi, *id);
 
             // handle explicit defs
             for (int i = instr->getNumOperands() - 1; i >= 0; --i) {
@@ -312,14 +312,9 @@ void LiveIntervals::computeIntervals()
                 if (!mop.isRegister())
                     continue;
 
-                unsigned reg = mop.getAllocatedRegNum();
                 // handle defs - build intervals
-                if (mop.isDef()) {
-                    if (reg < MRegisterInfo::FirstVirtualRegister)
-                        handlePhysicalRegisterDef(mbb, mi, reg);
-                    else
-                        handleVirtualRegisterDef(mbb, mi, reg);
-                }
+                if (mop.isDef())
+                    handleRegisterDef(mbb, mi, mop.getAllocatedRegNum());
             }
         }
     }
index a622b05160d6f8e9daae178005a463da07e51218..1bfc6e553d64207b646e8591250204e88eb0799e 100644 (file)
@@ -117,14 +117,6 @@ void LiveVariables::HandlePhysRegUse(unsigned Reg, MachineInstr *MI) {
   if (PhysRegInfo[Reg]) {
     PhysRegInfo[Reg] = MI;
     PhysRegUsed[Reg] = true;
-  } else {
-    for (const unsigned *AliasSet = RegInfo->getAliasSet(Reg);
-         *AliasSet; ++AliasSet) {
-      if (MachineInstr *LastUse = PhysRegInfo[*AliasSet]) {
-       PhysRegInfo[*AliasSet] = MI;
-       PhysRegUsed[*AliasSet] = true;
-      }
-    }
   }
 }
 
@@ -135,20 +127,21 @@ void LiveVariables::HandlePhysRegDef(unsigned Reg, MachineInstr *MI) {
       RegistersKilled.insert(std::make_pair(LastUse, Reg));
     else
       RegistersDead.insert(std::make_pair(LastUse, Reg));
-  } else {
-    for (const unsigned *AliasSet = RegInfo->getAliasSet(Reg);
-         *AliasSet; ++AliasSet) {
-      if (MachineInstr *LastUse = PhysRegInfo[*AliasSet]) {
-       if (PhysRegUsed[*AliasSet])
-         RegistersKilled.insert(std::make_pair(LastUse, *AliasSet));
-       else
-         RegistersDead.insert(std::make_pair(LastUse, *AliasSet));
-       PhysRegInfo[*AliasSet] = 0;  // Kill the aliased register
-      }
-    }
   }
   PhysRegInfo[Reg] = MI;
   PhysRegUsed[Reg] = false;
+
+  for (const unsigned *AliasSet = RegInfo->getAliasSet(Reg);
+       *AliasSet; ++AliasSet) {
+    if (MachineInstr *LastUse = PhysRegInfo[*AliasSet]) {
+      if (PhysRegUsed[*AliasSet])
+       RegistersKilled.insert(std::make_pair(LastUse, *AliasSet));
+      else
+       RegistersDead.insert(std::make_pair(LastUse, *AliasSet));
+    }
+    PhysRegInfo[*AliasSet] = MI;
+    PhysRegUsed[*AliasSet] = false;
+  }
 }
 
 bool LiveVariables::runOnMachineFunction(MachineFunction &MF) {
index 88699d0bcb489af08519b9a37b891166b8a29729..5ffe5afc4dba92359f32ae782dfa71040bf2ba3c 100644 (file)
@@ -232,9 +232,8 @@ void RA::removePhysReg(unsigned PhysReg) {
 
   std::vector<unsigned>::iterator It =
     std::find(PhysRegsUseOrder.begin(), PhysRegsUseOrder.end(), PhysReg);
-  assert(It != PhysRegsUseOrder.end() &&
-         "Spilled a physical register, but it was not in use list!");
-  PhysRegsUseOrder.erase(It);
+  if (It != PhysRegsUseOrder.end())
+    PhysRegsUseOrder.erase(It);
 }
 
 
@@ -550,6 +549,11 @@ void RA::AllocateBasicBlock(MachineBasicBlock &MBB) {
         spillPhysReg(MBB, I, Reg, true);  // Spill any existing value in the reg
         PhysRegsUsed[Reg] = 0;            // It is free and reserved now
         PhysRegsUseOrder.push_back(Reg);
+        for (const unsigned *AliasSet = RegInfo->getAliasSet(Reg);
+             *AliasSet; ++AliasSet) {
+            PhysRegsUseOrder.push_back(*AliasSet);
+            PhysRegsUsed[*AliasSet] = 0;  // It is free and reserved now
+        }
       }
 
     // Loop over the implicit defs, spilling them as well.
@@ -559,6 +563,11 @@ void RA::AllocateBasicBlock(MachineBasicBlock &MBB) {
       spillPhysReg(MBB, I, Reg);
       PhysRegsUseOrder.push_back(Reg);
       PhysRegsUsed[Reg] = 0;            // It is free and reserved now
+      for (const unsigned *AliasSet = RegInfo->getAliasSet(Reg);
+           *AliasSet; ++AliasSet) {
+          PhysRegsUseOrder.push_back(*AliasSet);
+          PhysRegsUsed[*AliasSet] = 0;  // It is free and reserved now
+      }
     }
 
     // Okay, we have allocated all of the source operands and spilled any values