forked from OSchip/llvm-project
ARM pop of a single register encodes as post-indexed LDR.
Per the ARM ARM, a 'pop' of a single register encodes as an LDR, not an LDM. llvm-svn: 137316
This commit is contained in:
parent
6c6a7fd692
commit
8ba76c6d5c
|
@ -136,6 +136,8 @@ class ARMAsmParser : public MCTargetAsmParser {
|
||||||
|
|
||||||
bool validateInstruction(MCInst &Inst,
|
bool validateInstruction(MCInst &Inst,
|
||||||
const SmallVectorImpl<MCParsedAsmOperand*> &Ops);
|
const SmallVectorImpl<MCParsedAsmOperand*> &Ops);
|
||||||
|
void processInstruction(MCInst &Inst,
|
||||||
|
const SmallVectorImpl<MCParsedAsmOperand*> &Ops);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ARMAsmParser(MCSubtargetInfo &_STI, MCAsmParser &_Parser)
|
ARMAsmParser(MCSubtargetInfo &_STI, MCAsmParser &_Parser)
|
||||||
|
@ -2856,6 +2858,30 @@ validateInstruction(MCInst &Inst,
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ARMAsmParser::
|
||||||
|
processInstruction(MCInst &Inst,
|
||||||
|
const SmallVectorImpl<MCParsedAsmOperand*> &Operands) {
|
||||||
|
switch (Inst.getOpcode()) {
|
||||||
|
case ARM::LDMIA_UPD:
|
||||||
|
// If this is a load of a single register via a 'pop', then we should use
|
||||||
|
// a post-indexed LDR instruction instead, per the ARM ARM.
|
||||||
|
if (static_cast<ARMOperand*>(Operands[0])->getToken() == "pop" &&
|
||||||
|
Inst.getNumOperands() == 5) {
|
||||||
|
MCInst TmpInst;
|
||||||
|
TmpInst.setOpcode(ARM::LDR_POST_IMM);
|
||||||
|
TmpInst.addOperand(Inst.getOperand(4)); // Rt
|
||||||
|
TmpInst.addOperand(Inst.getOperand(0)); // Rn_wb
|
||||||
|
TmpInst.addOperand(Inst.getOperand(1)); // Rn
|
||||||
|
TmpInst.addOperand(MCOperand::CreateReg(0)); // am2offset
|
||||||
|
TmpInst.addOperand(MCOperand::CreateImm(4));
|
||||||
|
TmpInst.addOperand(Inst.getOperand(2)); // CondCode
|
||||||
|
TmpInst.addOperand(Inst.getOperand(3));
|
||||||
|
Inst = TmpInst;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool ARMAsmParser::
|
bool ARMAsmParser::
|
||||||
MatchAndEmitInstruction(SMLoc IDLoc,
|
MatchAndEmitInstruction(SMLoc IDLoc,
|
||||||
SmallVectorImpl<MCParsedAsmOperand*> &Operands,
|
SmallVectorImpl<MCParsedAsmOperand*> &Operands,
|
||||||
|
@ -2871,6 +2897,10 @@ MatchAndEmitInstruction(SMLoc IDLoc,
|
||||||
if (validateInstruction(Inst, Operands))
|
if (validateInstruction(Inst, Operands))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
// Some instructions need post-processing to, for example, tweak which
|
||||||
|
// encoding is selected.
|
||||||
|
processInstruction(Inst, Operands);
|
||||||
|
|
||||||
Out.EmitInstruction(Inst);
|
Out.EmitInstruction(Inst);
|
||||||
return false;
|
return false;
|
||||||
case Match_MissingFeature:
|
case Match_MissingFeature:
|
||||||
|
|
|
@ -100,6 +100,14 @@ void ARMInstPrinter::printInst(const MCInst *MI, raw_ostream &O) {
|
||||||
printRegisterList(MI, 4, O);
|
printRegisterList(MI, 4, O);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (Opcode == ARM::LDR_POST_IMM && MI->getOperand(2).getReg() == ARM::SP &&
|
||||||
|
MI->getOperand(4).getImm() == 4) {
|
||||||
|
O << '\t' << "pop";
|
||||||
|
printPredicateOperand(MI, 5, O);
|
||||||
|
O << "\t{" << getRegisterName(MI->getOperand(0).getReg()) << "}";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// A8.6.355 VPUSH
|
// A8.6.355 VPUSH
|
||||||
if ((Opcode == ARM::VSTMSDB_UPD || Opcode == ARM::VSTMDDB_UPD) &&
|
if ((Opcode == ARM::VSTMSDB_UPD || Opcode == ARM::VSTMDDB_UPD) &&
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
define i64 @t(i64 %a) nounwind readonly {
|
define i64 @t(i64 %a) nounwind readonly {
|
||||||
entry:
|
entry:
|
||||||
; CHECK: str lr, [sp, #-4]!
|
; CHECK: str lr, [sp, #-4]!
|
||||||
; CHECK: ldr lr, [sp], #4
|
; CHECK: pop {lr}
|
||||||
%0 = load i64** @b, align 4
|
%0 = load i64** @b, align 4
|
||||||
%1 = load i64* %0, align 4
|
%1 = load i64* %0, align 4
|
||||||
%2 = mul i64 %1, %a
|
%2 = mul i64 %1, %a
|
||||||
|
|
|
@ -664,9 +664,6 @@ Lforward:
|
||||||
@ CHECK: ldmda r2!, {r1, r3, r4, r5, r6, sp} @ encoding: [0x7a,0x20,0x32,0xe8]
|
@ CHECK: ldmda r2!, {r1, r3, r4, r5, r6, sp} @ encoding: [0x7a,0x20,0x32,0xe8]
|
||||||
@ CHECK: ldmdb r2!, {r1, r3, r4, r5, r6, sp} @ encoding: [0x7a,0x20,0x32,0xe9]
|
@ CHECK: ldmdb r2!, {r1, r3, r4, r5, r6, sp} @ encoding: [0x7a,0x20,0x32,0xe9]
|
||||||
|
|
||||||
@------------------------------------------------------------------------------
|
|
||||||
@ FIXME: LDR*
|
|
||||||
@------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
@------------------------------------------------------------------------------
|
@------------------------------------------------------------------------------
|
||||||
@ LDREX/LDREXB/LDREXH/LDREXD
|
@ LDREX/LDREXB/LDREXH/LDREXD
|
||||||
|
@ -1064,8 +1061,7 @@ Lforward:
|
||||||
pop {r7}
|
pop {r7}
|
||||||
pop {r7, r8, r9, r10}
|
pop {r7, r8, r9, r10}
|
||||||
|
|
||||||
@ FIXME: pop of a single register should encode as "ldr r7, [sp], #4"
|
@ CHECK: pop {r7} @ encoding: [0x04,0x70,0x9d,0xe4]
|
||||||
@ CHECK-FIXME: pop {r7} @ encoding: [0x04,0x70,0x9d,0xe4]
|
|
||||||
@ CHECK: pop {r7, r8, r9, r10} @ encoding: [0x80,0x07,0xbd,0xe8]
|
@ CHECK: pop {r7, r8, r9, r10} @ encoding: [0x80,0x07,0xbd,0xe8]
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue