aboutsummaryrefslogtreecommitdiff
path: root/lib/Target/ARM/ARMRegisterInfo.cpp
diff options
context:
space:
mode:
authorEvan Cheng <evan.cheng@apple.com>2007-01-30 01:18:38 +0000
committerEvan Cheng <evan.cheng@apple.com>2007-01-30 01:18:38 +0000
commitd1b2c1e88fe4a7728ca9739b0f1c6fd90a19c5fd (patch)
treea06f37be3684c1db7e3e3182bf132703a45bc1b2 /lib/Target/ARM/ARMRegisterInfo.cpp
parent225dfe973bd85e36ff16fe7a08e458f285703cc9 (diff)
- In thumb mode, if size of MachineFunction is >= 2048, force LR to be
spilled (if it is not already). - If LR is spilled, use BL to implement far jumps. LR is not used as a GPR in thumb mode so it can be clobbered if it is properly spilled / restored in prologue / epilogue. - If LR is force spilled but no far jump has been emitted, try undo'ing the spill by: push lr -> delete pop pc -> bx lr git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@33650 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/ARM/ARMRegisterInfo.cpp')
-rw-r--r--lib/Target/ARM/ARMRegisterInfo.cpp20
1 files changed, 17 insertions, 3 deletions
diff --git a/lib/Target/ARM/ARMRegisterInfo.cpp b/lib/Target/ARM/ARMRegisterInfo.cpp
index 2accaf890e..07869e4cf8 100644
--- a/lib/Target/ARM/ARMRegisterInfo.cpp
+++ b/lib/Target/ARM/ARMRegisterInfo.cpp
@@ -770,17 +770,29 @@ processFunctionBeforeCalleeSavedScan(MachineFunction &MF) const {
}
ARMFunctionInfo *AFI = MF.getInfo<ARMFunctionInfo>();
+ bool ForceLRSpill = false;
+ if (!LRSpilled && AFI->isThumbFunction()) {
+ unsigned FnSize = ARM::GetFunctionSize(MF);
+ // Force LR spill if the Thumb function size is > 2048. This enables the
+ // use of BL to implement far jump. If it turns out that it's not needed
+ // the branch fix up path will undo it.
+ if (FnSize >= (1 << 11)) {
+ CanEliminateFrame = false;
+ ForceLRSpill = true;
+ }
+ }
+
if (!CanEliminateFrame) {
AFI->setHasStackFrame(true);
// If LR is not spilled, but at least one of R4, R5, R6, and R7 is spilled.
// Spill LR as well so we can fold BX_RET to the registers restore (LDM).
if (!LRSpilled && CS1Spilled) {
- LRSpilled = true;
MF.changePhyRegUsed(ARM::LR, true);
NumGPRSpills++;
UnspilledCS1GPRs.erase(std::find(UnspilledCS1GPRs.begin(),
UnspilledCS1GPRs.end(), (unsigned)ARM::LR));
+ ForceLRSpill = false;
}
if (STI.isTargetDarwin()) {
@@ -800,8 +812,10 @@ processFunctionBeforeCalleeSavedScan(MachineFunction &MF) const {
}
}
- // Remembe if LR has been spilled.
- AFI->setLRIsSpilled(LRSpilled);
+ if (ForceLRSpill) {
+ MF.changePhyRegUsed(ARM::LR, true);
+ AFI->setLRIsForceSpilled(true);
+ }
}
/// Move iterator pass the next bunch of callee save load / store ops for