[llvm-commits] [llvm] r83519 - in /llvm/trunk/lib/CodeGen: PrologEpilogInserter.cpp PrologEpilogInserter.h
Jim Grosbach
grosbach at apple.com
Wed Oct 7 18:09:45 PDT 2009
Author: grosbach
Date: Wed Oct 7 20:09:45 2009
New Revision: 83519
URL: http://llvm.org/viewvc/llvm-project?rev=83519&view=rev
Log:
bugfix. The target may use virtual registers that aren't tracked for re-use but are allocated by the scavenger. The re-use algorithm needs to watch for that.
Modified:
llvm/trunk/lib/CodeGen/PrologEpilogInserter.cpp
llvm/trunk/lib/CodeGen/PrologEpilogInserter.h
Modified: llvm/trunk/lib/CodeGen/PrologEpilogInserter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/PrologEpilogInserter.cpp?rev=83519&r1=83518&r2=83519&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/PrologEpilogInserter.cpp (original)
+++ llvm/trunk/lib/CodeGen/PrologEpilogInserter.cpp Wed Oct 7 20:09:45 2009
@@ -655,11 +655,6 @@
int FrameSetupOpcode = TRI.getCallFrameSetupOpcode();
int FrameDestroyOpcode = TRI.getCallFrameDestroyOpcode();
- // Pre-allocate space for frame index mappings. If more space is needed,
- // the map will be grown later.
- if (FrameIndexVirtualScavenging)
- FrameConstantRegMap.grow(Fn.getRegInfo().getLastVirtReg() + 128);
-
for (MachineFunction::iterator BB = Fn.begin(),
E = Fn.end(); BB != E; ++BB) {
int SPAdj = 0; // SP offset due to call frame setup / destroy.
@@ -716,7 +711,6 @@
assert (FrameIndexVirtualScavenging &&
"Not scavenging, but virtual returned from "
"eliminateFrameIndex()!");
- FrameConstantRegMap.grow(VReg);
FrameConstantRegMap[VReg] = FrameConstantEntry(Value, SPAdj);
}
@@ -780,10 +774,14 @@
unsigned CurrentVirtReg = 0;
unsigned CurrentScratchReg = 0;
+ bool havePrevValue = false;
unsigned PrevScratchReg = 0;
int PrevValue;
MachineInstr *PrevLastUseMI = NULL;
unsigned PrevLastUseOp = 0;
+ bool trackingCurrentValue = false;
+ int SPAdj = 0;
+ int Value = 0;
// The instruction stream may change in the loop, so check BB->end()
// directly.
@@ -818,14 +816,31 @@
continue;
}
- // If we already have a scratch for this virtual register, use it
+ // Have we already allocated a scratch register for this virtual?
if (Reg != CurrentVirtReg) {
- int Value = FrameConstantRegMap[Reg].first;
- int SPAdj = FrameConstantRegMap[Reg].second;
+ // When we first encounter a new virtual register, it
+ // must be a definition.
+ assert(MI->getOperand(i).isDef() &&
+ "frame index virtual missing def!");
+ // We can't have nested virtual register live ranges because
+ // there's only a guarantee of one scavenged register at a time.
+ assert (CurrentVirtReg == 0 &&
+ "overlapping frame index virtual registers!");
+
+ // If the target gave us information about what's in the register,
+ // we can use that to re-use scratch regs.
+ DenseMap<unsigned, FrameConstantEntry>::iterator Entry =
+ FrameConstantRegMap.find(Reg);
+ trackingCurrentValue = Entry != FrameConstantRegMap.end();
+ if (trackingCurrentValue) {
+ SPAdj = (*Entry).second.second;
+ Value = (*Entry).second.first;
+ } else
+ SPAdj = Value = 0;
// If the scratch register from the last allocation is still
// available, see if the value matches. If it does, just re-use it.
- if (PrevScratchReg && Value == PrevValue) {
+ if (trackingCurrentValue && havePrevValue && PrevValue == Value) {
// FIXME: This assumes that the instructions in the live range
// for the virtual register are exclusively for the purpose
// of populating the value in the register. That's reasonable
@@ -850,14 +865,6 @@
PrevLastUseMI->getOperand(PrevLastUseOp).setIsKill(false);
RS->setUsed(CurrentScratchReg);
} else {
- // When we first encounter a new virtual register, it
- // must be a definition.
- assert(MI->getOperand(i).isDef() &&
- "frame index virtual missing def!");
- // We can't have nested virtual register live ranges because
- // there's only a guarantee of one scavenged register at a time.
- assert (CurrentVirtReg == 0 &&
- "overlapping frame index virtual registers!");
CurrentVirtReg = Reg;
const TargetRegisterClass *RC = Fn.getRegInfo().getRegClass(Reg);
CurrentScratchReg = RS->FindUnusedReg(RC);
@@ -877,6 +884,7 @@
PrevLastUseMI = MI;
PrevLastUseOp = i;
CurrentScratchReg = CurrentVirtReg = 0;
+ havePrevValue = trackingCurrentValue;
}
}
RS->forward(MI);
Modified: llvm/trunk/lib/CodeGen/PrologEpilogInserter.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/PrologEpilogInserter.h?rev=83519&r1=83518&r2=83519&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/PrologEpilogInserter.h (original)
+++ llvm/trunk/lib/CodeGen/PrologEpilogInserter.h Wed Oct 7 20:09:45 2009
@@ -27,7 +27,6 @@
#include "llvm/CodeGen/MachineLoopInfo.h"
#include "llvm/ADT/SparseBitVector.h"
#include "llvm/ADT/DenseMap.h"
-#include "llvm/ADT/IndexedMap.h"
#include "llvm/Target/TargetRegisterInfo.h"
namespace llvm {
@@ -99,7 +98,7 @@
// materialization registers, maintain a map of the registers to
// the constant value and SP adjustment associated with it.
typedef std::pair<int, int> FrameConstantEntry;
- IndexedMap<FrameConstantEntry, VirtReg2IndexFunctor> FrameConstantRegMap;
+ DenseMap<unsigned, FrameConstantEntry> FrameConstantRegMap;
#ifndef NDEBUG
// Machine function handle.
More information about the llvm-commits
mailing list