Add coalescing to register allocator. A hint is added to each interval
authorAlkis Evlogimenos <alkis@evlogimenos.com>
Sun, 28 Dec 2003 17:58:18 +0000 (17:58 +0000)
committerAlkis Evlogimenos <alkis@evlogimenos.com>
Sun, 28 Dec 2003 17:58:18 +0000 (17:58 +0000)
which denotes the register we would like to be assigned to (virtual or
physical). In register allocation, if this hint exists and we can map
it to a physical register (it is either a physical register or it is a
virtual register that already got assigned to a physical one) we use
that register if it is available instead of a random one in the free
pool.

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

include/llvm/CodeGen/LiveIntervalAnalysis.h
include/llvm/CodeGen/LiveIntervals.h
lib/CodeGen/LiveIntervalAnalysis.cpp
lib/CodeGen/LiveIntervalAnalysis.h
lib/CodeGen/RegAllocLinearScan.cpp

index cecfbbadbdfb98c832757f565df632cbcedf31e1..8f5fd3a648d94f56ebcc5a5609b678cd9cccb818 100644 (file)
@@ -38,6 +38,7 @@ namespace llvm {
             typedef std::pair<unsigned, unsigned> Range;
             typedef std::vector<Range> Ranges;
             unsigned reg;   // the register of this interval
+            unsigned hint;
             float weight;   // weight of this interval (number of uses
                             // * 10^loopDepth)
             Ranges ranges;  // the ranges this register is valid
index cecfbbadbdfb98c832757f565df632cbcedf31e1..8f5fd3a648d94f56ebcc5a5609b678cd9cccb818 100644 (file)
@@ -38,6 +38,7 @@ namespace llvm {
             typedef std::pair<unsigned, unsigned> Range;
             typedef std::vector<Range> Ranges;
             unsigned reg;   // the register of this interval
+            unsigned hint;
             float weight;   // weight of this interval (number of uses
                             // * 10^loopDepth)
             Ranges ranges;  // the ranges this register is valid
index b34a65bc6443577dbd6b3b614ae86e52de804cde..4d0916046a0f4d45989d2913e19f8bd2856601b7 100644 (file)
@@ -108,6 +108,7 @@ bool LiveIntervals::runOnMachineFunction(MachineFunction &fn) {
 
     // compute spill weights
     const LoopInfo& loopInfo = getAnalysis<LoopInfo>();
+    const TargetInstrInfo& tii = tm_->getInstrInfo();
 
     for (MbbIndex2MbbMap::iterator
              it = mbbi2mbbMap_.begin(), itEnd = mbbi2mbbMap_.end();
@@ -130,6 +131,21 @@ bool LiveIntervals::runOnMachineFunction(MachineFunction &fn) {
                 assert(r2iit != r2iMap_.end());
                 intervals_[r2iit->second].weight += pow(10.0F, loopDepth);
             }
+
+            // add hints for coalescing
+            unsigned src, dst;
+            if (tii.isMoveInstr(*instr, src, dst)) {
+                if (src >= MRegisterInfo::FirstVirtualRegister) {
+                    Reg2IntervalMap::iterator r2iit = r2iMap_.find(src);
+                    assert(r2iit != r2iMap_.end());
+                    intervals_[r2iit->second].hint = dst;
+                }
+                if (dst >= MRegisterInfo::FirstVirtualRegister) {
+                    Reg2IntervalMap::iterator r2iit = r2iMap_.find(dst);
+                    assert(r2iit != r2iMap_.end());
+                    intervals_[r2iit->second].hint = src;
+                }
+            }
         }
     }
 
@@ -329,7 +345,7 @@ void LiveIntervals::computeIntervals()
 }
 
 LiveIntervals::Interval::Interval(unsigned r)
-    : reg(r),
+    : reg(r), hint(0),
       weight((r < MRegisterInfo::FirstVirtualRegister ?
               std::numeric_limits<float>::max() : 0.0F))
 {
index cecfbbadbdfb98c832757f565df632cbcedf31e1..8f5fd3a648d94f56ebcc5a5609b678cd9cccb818 100644 (file)
@@ -38,6 +38,7 @@ namespace llvm {
             typedef std::pair<unsigned, unsigned> Range;
             typedef std::vector<Range> Ranges;
             unsigned reg;   // the register of this interval
+            unsigned hint;
             float weight;   // weight of this interval (number of uses
                             // * 10^loopDepth)
             Ranges ranges;  // the ranges this register is valid
index a804e1aa8697b96967885922f952c1daa1611d15..e2c1a18b4403969eb342ca321a24360026132775 100644 (file)
@@ -615,8 +615,19 @@ bool RA::physRegAvailable(unsigned physReg)
 unsigned RA::getFreePhysReg(Intervals::const_iterator cur)
 {
     DEBUG(std::cerr << "\t\tgetting free physical register: ");
-
     const TargetRegisterClass* rc = mf_->getSSARegMap()->getRegClass(cur->reg);
+
+    if (unsigned reg = cur->hint) {
+        if (reg >= MRegisterInfo::FirstVirtualRegister &&
+            v2pMap_.find(reg) != v2pMap_.end())
+            reg = v2pMap_[reg];
+        if (reg && reg < MRegisterInfo::FirstVirtualRegister &&
+            mri_->getRegClass(reg) == rc && !regUse_[reg]) {
+            DEBUG(std::cerr << mri_->getName(reg) << '\n');
+            return reg;
+        }
+    }
+            
     for (TargetRegisterClass::iterator i = rc->allocation_order_begin(*mf_);
          i != rc->allocation_order_end(*mf_); ++i) {
         unsigned reg = *i;