[llvm-commits] CVS: llvm/lib/Target/ARM/ARMRegisterInfo.cpp
Evan Cheng
evan.cheng at apple.com
Wed Feb 7 00:37:56 PST 2007
Changes in directory llvm/lib/Target/ARM:
ARMRegisterInfo.cpp updated: 1.60 -> 1.61
---
Log message:
- If fp (r7) is used to reference stack objects, use [r, r] address mode.
- If there is a dynamic alloca, in the epilogue, restore the value of sp
using r7 - offset.
- Other bug fixes.
---
Diffs of the changes: (+67 -28)
ARMRegisterInfo.cpp | 95 ++++++++++++++++++++++++++++++++++++----------------
1 files changed, 67 insertions(+), 28 deletions(-)
Index: llvm/lib/Target/ARM/ARMRegisterInfo.cpp
diff -u llvm/lib/Target/ARM/ARMRegisterInfo.cpp:1.60 llvm/lib/Target/ARM/ARMRegisterInfo.cpp:1.61
--- llvm/lib/Target/ARM/ARMRegisterInfo.cpp:1.60 Tue Feb 6 20:44:23 2007
+++ llvm/lib/Target/ARM/ARMRegisterInfo.cpp Wed Feb 7 02:37:31 2007
@@ -359,6 +359,19 @@
return NumMIs;
}
+/// emitLoadConstPool - Emits a load from constpool to materialize NumBytes
+/// immediate.
+static void emitLoadConstPool(MachineBasicBlock &MBB,
+ MachineBasicBlock::iterator &MBBI,
+ unsigned DestReg, int NumBytes,
+ const TargetInstrInfo &TII) {
+ MachineFunction &MF = *MBB.getParent();
+ MachineConstantPool *ConstantPool = MF.getConstantPool();
+ Constant *C = ConstantInt::get(Type::Int32Ty, NumBytes);
+ unsigned Idx = ConstantPool->getConstantPoolIndex(C, 2);
+ BuildMI(MBB, MBBI, TII.get(ARM::tLDRpci), DestReg).addConstantPoolIndex(Idx);
+}
+
/// emitThumbRegPlusConstPool - Emits a series of instructions to materialize
/// a destreg = basereg + immediate in Thumb code. Load the immediate from a
/// constpool entry.
@@ -368,9 +381,8 @@
unsigned DestReg, unsigned BaseReg,
int NumBytes, bool CanChangeCC,
const TargetInstrInfo &TII) {
- MachineFunction &MF = *MBB.getParent();
- MachineConstantPool *ConstantPool = MF.getConstantPool();
- bool isHigh = !isLowRegister(DestReg) || !isLowRegister(BaseReg);
+ bool isHigh = !isLowRegister(DestReg) ||
+ (BaseReg != 0 && !isLowRegister(BaseReg));
bool isSub = false;
// Subtract doesn't have high register version. Load the negative value
// if either base or dest register is a high register. Also, if do not
@@ -389,12 +401,9 @@
if (NumBytes <= 255 && NumBytes >= 0)
BuildMI(MBB, MBBI, TII.get(ARM::tMOVri8), LdReg).addImm(NumBytes);
- else {
- // Load the constant.
- Constant *C = ConstantInt::get(Type::Int32Ty, NumBytes);
- unsigned Idx = ConstantPool->getConstantPoolIndex(C, 2);
- BuildMI(MBB, MBBI, TII.get(ARM::tLDRpci), LdReg).addConstantPoolIndex(Idx);
- }
+ else
+ emitLoadConstPool(MBB, MBBI, LdReg, NumBytes, TII);
+
// Emit add / sub.
int Opc = (isSub) ? ARM::tSUBrr : (isHigh ? ARM::tADDhirr : ARM::tADDrr);
const MachineInstrBuilder MIB = BuildMI(MBB, MBBI, TII.get(Opc), DestReg);
@@ -721,8 +730,8 @@
case ARMII::AddrModeTs: {
ImmIdx = i+1;
InstrOffs = MI.getOperand(ImmIdx).getImm();
- NumBits = isSub ? 3 : ((FrameReg == ARM::SP) ? 8 : 5);
- Scale = isSub ? 1 : 4;
+ NumBits = (FrameReg == ARM::SP) ? 8 : 5;
+ Scale = 4;
break;
}
default:
@@ -754,7 +763,7 @@
// If this is a thumb spill / restore, we will be using a constpool load to
// materialize the offset.
bool isThumSpillRestore = Opcode == ARM::tRestore || Opcode == ARM::tSpill;
- if (AddrMode == ARMII::AddrModeTs || !isThumSpillRestore) {
+ if (AddrMode == ARMII::AddrModeTs && !isThumSpillRestore) {
if (AddrMode == ARMII::AddrModeTs) {
// Thumb tLDRspi, tSTRspi. These will change to instructions that use
// a different base register.
@@ -779,12 +788,21 @@
if (TII.isLoad(Opcode)) {
// Use the destination register to materialize sp + offset.
unsigned TmpReg = MI.getOperand(0).getReg();
- if (Opcode == ARM::tRestore)
- emitThumbRegPlusConstPool(MBB, II, TmpReg, FrameReg, Offset, false, TII);
- else
+ bool UseRR = false;
+ if (Opcode == ARM::tRestore) {
+ if (FrameReg == ARM::SP)
+ emitThumbRegPlusConstPool(MBB, II, TmpReg, FrameReg,Offset,false,TII);
+ else {
+ emitLoadConstPool(MBB, II, TmpReg, Offset, TII);
+ UseRR = true;
+ }
+ } else
emitThumbRegPlusImmediate(MBB, II, TmpReg, FrameReg, Offset, TII);
MI.setInstrDescriptor(TII.get(ARM::tLDR));
MI.getOperand(i).ChangeToRegister(TmpReg, false);
+ if (UseRR)
+ MI.addRegOperand(FrameReg, false); // Use [reg, reg] addrmode.
+ else
MI.addRegOperand(0, false); // tLDR has an extra register operand.
} else if (TII.isStore(Opcode)) {
// FIXME! This is horrific!!! We need register scavenging.
@@ -797,19 +815,30 @@
// r2 = r12
unsigned ValReg = MI.getOperand(0).getReg();
unsigned TmpReg = ARM::R3;
+ bool UseRR = false;
if (ValReg == ARM::R3) {
BuildMI(MBB, II, TII.get(ARM::tMOVrr), ARM::R12).addReg(ARM::R2);
TmpReg = ARM::R2;
}
- if (Opcode == ARM::tSpill)
- emitThumbRegPlusConstPool(MBB, II, TmpReg, FrameReg, Offset, false, TII);
- else
+ if (Opcode == ARM::tSpill) {
+ if (FrameReg == ARM::SP)
+ emitThumbRegPlusConstPool(MBB, II, TmpReg, FrameReg,Offset,false,TII);
+ else {
+ emitLoadConstPool(MBB, II, TmpReg, Offset, TII);
+ UseRR = true;
+ }
+ } else
emitThumbRegPlusImmediate(MBB, II, TmpReg, FrameReg, Offset, TII);
MI.setInstrDescriptor(TII.get(ARM::tSTR));
MI.getOperand(i).ChangeToRegister(TmpReg, false);
- MI.addRegOperand(0, false); // tSTR has an extra register operand.
- if (ValReg == ARM::R3)
- BuildMI(MBB, II, TII.get(ARM::tMOVrr), ARM::R2).addReg(ARM::R12);
+ if (UseRR)
+ MI.addRegOperand(FrameReg, false); // Use [reg, reg] addrmode.
+ else
+ MI.addRegOperand(0, false); // tSTR has an extra register operand.
+ if (ValReg == ARM::R3) {
+ MachineBasicBlock::iterator NII = next(II);
+ BuildMI(MBB, NII, TII.get(ARM::tMOVrr), ARM::R2).addReg(ARM::R12);
+ }
} else
assert(false && "Unexpected opcode!");
} else {
@@ -1152,13 +1181,23 @@
AFI->getGPRCalleeSavedArea2Size() +
AFI->getDPRCalleeSavedAreaSize());
if (isThumb) {
- if (MBBI->getOpcode() == ARM::tBX_RET &&
- &MBB.front() != MBBI &&
- prior(MBBI)->getOpcode() == ARM::tPOP) {
- MachineBasicBlock::iterator PMBBI = prior(MBBI);
- emitSPUpdate(MBB, PMBBI, NumBytes, isThumb, TII);
- } else
- emitSPUpdate(MBB, MBBI, NumBytes, isThumb, TII);
+ if (hasFP(MF)) {
+ NumBytes = AFI->getFramePtrSpillOffset() - NumBytes;
+ // Reset SP based on frame pointer only if the stack frame extends beyond
+ // frame pointer stack slot or target is ELF and the function has FP.
+ if (NumBytes)
+ emitThumbRegPlusImmediate(MBB, MBBI, ARM::SP, FramePtr, -NumBytes, TII);
+ else
+ BuildMI(MBB, MBBI, TII.get(ARM::tMOVrr), ARM::SP).addReg(FramePtr);
+ } else {
+ if (MBBI->getOpcode() == ARM::tBX_RET &&
+ &MBB.front() != MBBI &&
+ prior(MBBI)->getOpcode() == ARM::tPOP) {
+ MachineBasicBlock::iterator PMBBI = prior(MBBI);
+ emitSPUpdate(MBB, PMBBI, NumBytes, isThumb, TII);
+ } else
+ emitSPUpdate(MBB, MBBI, NumBytes, isThumb, TII);
+ }
} else {
// Darwin ABI requires FP to point to the stack slot that contains the
// previous FP.
More information about the llvm-commits
mailing list