summaryrefslogtreecommitdiff
path: root/lib/Target/ARM/Thumb2InstrInfo.cpp
diff options
context:
space:
mode:
authorEvan Cheng <evan.cheng@apple.com>2009-08-27 01:23:50 +0000
committerEvan Cheng <evan.cheng@apple.com>2009-08-27 01:23:50 +0000
commitcdbb3f5d3311e0f46d22bc8daa211b2fab3541cb (patch)
tree3c611bd106d479bc12372a51fcee8037f877da46 /lib/Target/ARM/Thumb2InstrInfo.cpp
parent8dcf70080280dcf8d6861f2da9f8f9dd1a61aed6 (diff)
downloadllvm-cdbb3f5d3311e0f46d22bc8daa211b2fab3541cb.tar.gz
llvm-cdbb3f5d3311e0f46d22bc8daa211b2fab3541cb.tar.bz2
llvm-cdbb3f5d3311e0f46d22bc8daa211b2fab3541cb.tar.xz
Fix PR4789. Teach eliminateFrameIndex how to handle VLDRQ and VSTRQ which cannot fold any immediate offset.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@80191 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/ARM/Thumb2InstrInfo.cpp')
-rw-r--r--lib/Target/ARM/Thumb2InstrInfo.cpp36
1 files changed, 22 insertions, 14 deletions
diff --git a/lib/Target/ARM/Thumb2InstrInfo.cpp b/lib/Target/ARM/Thumb2InstrInfo.cpp
index d37f61e490..8c09ebd3e0 100644
--- a/lib/Target/ARM/Thumb2InstrInfo.cpp
+++ b/lib/Target/ARM/Thumb2InstrInfo.cpp
@@ -319,9 +319,9 @@ immediateOffsetOpcode(unsigned opcode)
return 0;
}
-int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
- unsigned FrameReg, int Offset,
- const ARMBaseInstrInfo &TII) {
+bool llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
+ unsigned FrameReg, int &Offset,
+ const ARMBaseInstrInfo &TII) {
unsigned Opcode = MI.getOpcode();
const TargetInstrDesc &Desc = MI.getDesc();
unsigned AddrMode = (Desc.TSFlags & ARMII::AddrModeMask);
@@ -340,7 +340,8 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
MI.setDesc(TII.get(ARM::tMOVgpr2gpr));
MI.getOperand(FrameRegIdx).ChangeToRegister(FrameReg, false);
MI.RemoveOperand(FrameRegIdx+1);
- return 0;
+ Offset = 0;
+ return true;
}
if (Offset < 0) {
@@ -355,7 +356,8 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
if (ARM_AM::getT2SOImmVal(Offset) != -1) {
MI.getOperand(FrameRegIdx).ChangeToRegister(FrameReg, false);
MI.getOperand(FrameRegIdx+1).ChangeToImmediate(Offset);
- return 0;
+ Offset = 0;
+ return true;
}
// Another common case: imm12.
if (Offset < 4096) {
@@ -365,7 +367,8 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
MI.setDesc(TII.get(NewOpc));
MI.getOperand(FrameRegIdx).ChangeToRegister(FrameReg, false);
MI.getOperand(FrameRegIdx+1).ChangeToImmediate(Offset);
- return 0;
+ Offset = 0;
+ return true;
}
// Otherwise, extract 8 adjacent bits from the immediate into this
@@ -387,7 +390,7 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
unsigned OffsetReg = MI.getOperand(FrameRegIdx+1).getReg();
if (OffsetReg != 0) {
MI.getOperand(FrameRegIdx).ChangeToRegister(FrameReg, false);
- return Offset;
+ return Offset == 0;
}
MI.RemoveOperand(FrameRegIdx+1);
@@ -413,11 +416,14 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
NumBits = 12;
}
} else {
- // VFP address modes.
- assert(AddrMode == ARMII::AddrMode5);
- int InstrOffs=ARM_AM::getAM5Offset(MI.getOperand(FrameRegIdx+1).getImm());
- if (ARM_AM::getAM5Op(MI.getOperand(FrameRegIdx+1).getImm()) ==ARM_AM::sub)
- InstrOffs *= -1;
+ // VFP and NEON address modes.
+ int InstrOffs = 0;
+ if (AddrMode == ARMII::AddrMode5) {
+ const MachineOperand &OffOp = MI.getOperand(FrameRegIdx+1);
+ InstrOffs = ARM_AM::getAM5Offset(OffOp.getImm());
+ if (ARM_AM::getAM5Op(OffOp.getImm()) == ARM_AM::sub)
+ InstrOffs *= -1;
+ }
NumBits = 8;
Scale = 4;
Offset += InstrOffs * 4;
@@ -448,7 +454,8 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
ImmedOffset = -ImmedOffset;
}
ImmOp.ChangeToImmediate(ImmedOffset);
- return 0;
+ Offset = 0;
+ return true;
}
// Otherwise, offset doesn't fit. Pull in what we can to simplify
@@ -468,5 +475,6 @@ int llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
Offset &= ~(Mask*Scale);
}
- return (isSub) ? -Offset : Offset;
+ Offset = (isSub) ? -Offset : Offset;
+ return Offset == 0;
}