X-Git-Url: http://demsky.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FCodeGen%2FRegAllocBasic.cpp;h=6b01ccb30940a729f6c78d7dcb4bb495668d14cc;hb=f152fe8d487c46873bbdd4abab43200f783e978b;hp=cb92513d8ec1567fd8ff1110fe3f1c407b984725;hpb=96f678f2d78ae9a2a8c99ca612bf59c056b36797;p=oota-llvm.git diff --git a/lib/CodeGen/RegAllocBasic.cpp b/lib/CodeGen/RegAllocBasic.cpp index cb92513d8ec..6b01ccb3094 100644 --- a/lib/CodeGen/RegAllocBasic.cpp +++ b/lib/CodeGen/RegAllocBasic.cpp @@ -15,7 +15,6 @@ #define DEBUG_TYPE "regalloc" #include "RegAllocBase.h" #include "LiveDebugVariables.h" -#include "LiveRangeEdit.h" #include "RenderMachineFunction.h" #include "Spiller.h" #include "VirtRegMap.h" @@ -24,6 +23,7 @@ #include "llvm/PassAnalysisSupport.h" #include "llvm/CodeGen/CalcSpillWeights.h" #include "llvm/CodeGen/LiveIntervalAnalysis.h" +#include "llvm/CodeGen/LiveRangeEdit.h" #include "llvm/CodeGen/LiveStackAnalysis.h" #include "llvm/CodeGen/MachineFunctionPass.h" #include "llvm/CodeGen/MachineInstr.h" @@ -72,6 +72,11 @@ class RABasic : public MachineFunctionPass, public RegAllocBase std::auto_ptr SpillerInstance; std::priority_queue, CompSpillWeight> Queue; + + // Scratch space. Allocated here to avoid repeated malloc calls in + // selectOrSplit(). + BitVector UsableRegs; + public: RABasic(); @@ -127,9 +132,8 @@ RABasic::RABasic(): MachineFunctionPass(ID) { initializeLiveDebugVariablesPass(*PassRegistry::getPassRegistry()); initializeLiveIntervalsPass(*PassRegistry::getPassRegistry()); initializeSlotIndexesPass(*PassRegistry::getPassRegistry()); - initializeStrongPHIEliminationPass(*PassRegistry::getPassRegistry()); initializeRegisterCoalescerPass(*PassRegistry::getPassRegistry()); - initializeMachineSchedulerPassPass(*PassRegistry::getPassRegistry()); + initializeMachineSchedulerPass(*PassRegistry::getPassRegistry()); initializeCalculateSpillWeightsPass(*PassRegistry::getPassRegistry()); initializeLiveStacksPass(*PassRegistry::getPassRegistry()); initializeMachineDominatorTreePass(*PassRegistry::getPassRegistry()); @@ -146,11 +150,6 @@ void RABasic::getAnalysisUsage(AnalysisUsage &AU) const { AU.addPreserved(); AU.addRequired(); AU.addPreserved(); - if (StrongPHIElim) - AU.addRequiredID(StrongPHIEliminationID); - AU.addRequiredTransitiveID(RegisterCoalescerPassID); - if (EnableMachineSched) - AU.addRequiredID(MachineSchedulerPassID); AU.addRequired(); AU.addRequired(); AU.addPreserved(); @@ -188,7 +187,7 @@ void RABasic::spillReg(LiveInterval& VirtReg, unsigned PhysReg, unassign(SpilledVReg, PhysReg); // Spill the extracted interval. - LiveRangeEdit LRE(SpilledVReg, SplitVRegs, 0, &PendingSpills); + LiveRangeEdit LRE(&SpilledVReg, SplitVRegs, *MF, *LIS, VRM); spiller().spill(LRE); } // After extracting segments, the query's results are invalid. But keep the @@ -205,7 +204,7 @@ bool RABasic::spillInterferences(LiveInterval &VirtReg, unsigned PhysReg, // either the union or live intervals. unsigned NumInterferences = 0; // Collect interferences assigned to any alias of the physical register. - for (const unsigned *asI = TRI->getOverlaps(PhysReg); *asI; ++asI) { + for (const uint16_t *asI = TRI->getOverlaps(PhysReg); *asI; ++asI) { LiveIntervalUnion::Query &QAlias = query(VirtReg, *asI); NumInterferences += QAlias.collectInterferingVRegs(); if (QAlias.seenUnspillableVReg()) { @@ -217,7 +216,7 @@ bool RABasic::spillInterferences(LiveInterval &VirtReg, unsigned PhysReg, assert(NumInterferences > 0 && "expect interference"); // Spill each interfering vreg allocated to PhysReg or an alias. - for (const unsigned *AliasI = TRI->getOverlaps(PhysReg); *AliasI; ++AliasI) + for (const uint16_t *AliasI = TRI->getOverlaps(PhysReg); *AliasI; ++AliasI) spillReg(VirtReg, *AliasI, SplitVRegs); return true; } @@ -236,6 +235,10 @@ bool RABasic::spillInterferences(LiveInterval &VirtReg, unsigned PhysReg, // selectOrSplit(). unsigned RABasic::selectOrSplit(LiveInterval &VirtReg, SmallVectorImpl &SplitVRegs) { + // Check for register mask interference. When live ranges cross calls, the + // set of usable registers is reduced to the callee-saved ones. + bool CrossRegMasks = LIS->checkRegMaskInterference(VirtReg, UsableRegs); + // Populate a list of physical register spill candidates. SmallVector PhysRegSpillCands; @@ -246,6 +249,11 @@ unsigned RABasic::selectOrSplit(LiveInterval &VirtReg, ++I) { unsigned PhysReg = *I; + // If PhysReg is clobbered by a register mask, it isn't useful for + // allocation or spilling. + if (CrossRegMasks && !UsableRegs.test(PhysReg)) + continue; + // Check interference and as a side effect, intialize queries for this // VirtReg and its aliases. unsigned interfReg = checkPhysRegInterference(VirtReg, PhysReg); @@ -279,7 +287,7 @@ unsigned RABasic::selectOrSplit(LiveInterval &VirtReg, DEBUG(dbgs() << "spilling: " << VirtReg << '\n'); if (!VirtReg.isSpillable()) return ~0u; - LiveRangeEdit LRE(VirtReg, SplitVRegs); + LiveRangeEdit LRE(&VirtReg, SplitVRegs, *MF, *LIS, VRM); spiller().spill(LRE); // The live virtual register requesting allocation was spilled, so tell @@ -334,7 +342,10 @@ bool RABasic::runOnMachineFunction(MachineFunction &mf) { // Write out new DBG_VALUE instructions. getAnalysis().emitDebugValues(VRM); - // The pass output is in VirtRegMap. Release all the transient data. + // All machine operands and other references to virtual registers have been + // replaced. Remove the virtual registers and release all the transient data. + VRM->clearAllVirt(); + MRI->clearVirtRegs(); releaseMemory(); return true;