The purpose of the patch is to fix the syntax of ARM mrc and mrc2 instructions when they are used to write to the APSR. In this case, the destination operand should be APSR_nzcv, and the encoding of the target should be 0b1111 (same as for PC). In pre-UAL syntax, this form used the PC register as a textual target. This is still allowed for backward compatibility.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@181705 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Mihai Popa 2013-05-13 14:10:04 +00:00
parent d26c93d3a8
commit f86e436fb9
6 changed files with 57 additions and 13 deletions

View File

@ -94,6 +94,7 @@ getReservedRegs(const MachineFunction &MF) const {
Reserved.set(ARM::SP); Reserved.set(ARM::SP);
Reserved.set(ARM::PC); Reserved.set(ARM::PC);
Reserved.set(ARM::FPSCR); Reserved.set(ARM::FPSCR);
Reserved.set(ARM::APSR_NZCV);
if (TFI->hasFP(MF)) if (TFI->hasFP(MF))
Reserved.set(FramePtr); Reserved.set(FramePtr);
if (hasBasePointer(MF)) if (hasBasePointer(MF))

View File

@ -4636,11 +4636,11 @@ def : ARMInstAlias<"mcr${p} $cop, $opc1, $Rt, $CRn, $CRm",
(MCR p_imm:$cop, imm0_7:$opc1, GPR:$Rt, c_imm:$CRn, (MCR p_imm:$cop, imm0_7:$opc1, GPR:$Rt, c_imm:$CRn,
c_imm:$CRm, 0, pred:$p)>; c_imm:$CRm, 0, pred:$p)>;
def MRC : MovRCopro<"mrc", 1 /* from coprocessor to ARM core register */, def MRC : MovRCopro<"mrc", 1 /* from coprocessor to ARM core register */,
(outs GPR:$Rt), (outs GPRwithAPSR:$Rt),
(ins p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, c_imm:$CRm, (ins p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, c_imm:$CRm,
imm0_7:$opc2), []>; imm0_7:$opc2), []>;
def : ARMInstAlias<"mrc${p} $cop, $opc1, $Rt, $CRn, $CRm", def : ARMInstAlias<"mrc${p} $cop, $opc1, $Rt, $CRn, $CRm",
(MRC GPR:$Rt, p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, (MRC GPRwithAPSR:$Rt, p_imm:$cop, imm0_7:$opc1, c_imm:$CRn,
c_imm:$CRm, 0, pred:$p)>; c_imm:$CRm, 0, pred:$p)>;
def : ARMPat<(int_arm_mrc imm:$cop, imm:$opc1, imm:$CRn, imm:$CRm, imm:$opc2), def : ARMPat<(int_arm_mrc imm:$cop, imm:$opc1, imm:$CRn, imm:$CRm, imm:$opc2),
@ -4650,7 +4650,7 @@ class MovRCopro2<string opc, bit direction, dag oops, dag iops,
list<dag> pattern> list<dag> pattern>
: ABXI<0b1110, oops, iops, NoItinerary, : ABXI<0b1110, oops, iops, NoItinerary,
!strconcat(opc, "\t$cop, $opc1, $Rt, $CRn, $CRm, $opc2"), pattern> { !strconcat(opc, "\t$cop, $opc1, $Rt, $CRn, $CRm, $opc2"), pattern> {
let Inst{31-28} = 0b1111; let Inst{31-24} = 0b11111110;
let Inst{20} = direction; let Inst{20} = direction;
let Inst{4} = 1; let Inst{4} = 1;
@ -4679,11 +4679,11 @@ def : ARMInstAlias<"mcr2$ $cop, $opc1, $Rt, $CRn, $CRm",
(MCR2 p_imm:$cop, imm0_7:$opc1, GPR:$Rt, c_imm:$CRn, (MCR2 p_imm:$cop, imm0_7:$opc1, GPR:$Rt, c_imm:$CRn,
c_imm:$CRm, 0)>; c_imm:$CRm, 0)>;
def MRC2 : MovRCopro2<"mrc2", 1 /* from coprocessor to ARM core register */, def MRC2 : MovRCopro2<"mrc2", 1 /* from coprocessor to ARM core register */,
(outs GPR:$Rt), (outs GPRwithAPSR:$Rt),
(ins p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, c_imm:$CRm, (ins p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, c_imm:$CRm,
imm0_7:$opc2), []>; imm0_7:$opc2), []>;
def : ARMInstAlias<"mrc2$ $cop, $opc1, $Rt, $CRn, $CRm", def : ARMInstAlias<"mrc2$ $cop, $opc1, $Rt, $CRn, $CRm",
(MRC2 GPR:$Rt, p_imm:$cop, imm0_7:$opc1, c_imm:$CRn, (MRC2 GPRwithAPSR:$Rt, p_imm:$cop, imm0_7:$opc1, c_imm:$CRn,
c_imm:$CRm, 0)>; c_imm:$CRm, 0)>;
def : ARMV5TPat<(int_arm_mrc2 imm:$cop, imm:$opc1, imm:$CRn, def : ARMV5TPat<(int_arm_mrc2 imm:$cop, imm:$opc1, imm:$CRn,

View File

@ -157,12 +157,15 @@ def Q15 : ARMReg<15, "q15", [D30, D31]>;
// Current Program Status Register. // Current Program Status Register.
// We model fpscr with two registers: FPSCR models the control bits and will be // We model fpscr with two registers: FPSCR models the control bits and will be
// reserved. FPSCR_NZCV models the flag bits and will be unreserved. // reserved. FPSCR_NZCV models the flag bits and will be unreserved. APSR_NZCV
def CPSR : ARMReg<0, "cpsr">; // models the APSR when it's accessed by some special instructions. In such cases
def APSR : ARMReg<1, "apsr">; // it has the same encoding as PC.
def SPSR : ARMReg<2, "spsr">; def CPSR : ARMReg<0, "cpsr">;
def FPSCR : ARMReg<3, "fpscr">; def APSR : ARMReg<1, "apsr">;
def FPSCR_NZCV : ARMReg<3, "fpscr_nzcv"> { def APSR_NZCV : ARMReg<15, "apsr_nzcv">;
def SPSR : ARMReg<2, "spsr">;
def FPSCR : ARMReg<3, "fpscr">;
def FPSCR_NZCV : ARMReg<3, "fpscr_nzcv"> {
let Aliases = [FPSCR]; let Aliases = [FPSCR];
} }
def ITSTATE : ARMReg<4, "itstate">; def ITSTATE : ARMReg<4, "itstate">;
@ -207,6 +210,16 @@ def GPRnopc : RegisterClass<"ARM", [i32], 32, (sub GPR, PC)> {
}]; }];
} }
// GPRs without the PC but with APSR. Some instructions allow accessing the
// APSR, while actually encoding PC in the register field. This is usefull
// for assembly and disassembly only.
def GPRwithAPSR : RegisterClass<"ARM", [i32], 32, (add GPR, APSR_NZCV)> {
let AltOrders = [(add LR, GPRnopc), (trunc GPRnopc, 8)];
let AltOrderSelect = [{
return 1 + MF.getTarget().getSubtarget<ARMSubtarget>().isThumb1Only();
}];
}
// GPRsp - Only the SP is legal. Used by Thumb1 instructions that want the // GPRsp - Only the SP is legal. Used by Thumb1 instructions that want the
// implied SP argument list. // implied SP argument list.
// FIXME: It would be better to not use this at all and refactor the // FIXME: It would be better to not use this at all and refactor the

View File

@ -156,6 +156,9 @@ static DecodeStatus DecodeGPRRegisterClass(MCInst &Inst, unsigned RegNo,
static DecodeStatus DecodeGPRnopcRegisterClass(MCInst &Inst, static DecodeStatus DecodeGPRnopcRegisterClass(MCInst &Inst,
unsigned RegNo, uint64_t Address, unsigned RegNo, uint64_t Address,
const void *Decoder); const void *Decoder);
static DecodeStatus DecodeGPRwithAPSRRegisterClass(MCInst &Inst,
unsigned RegNo, uint64_t Address,
const void *Decoder);
static DecodeStatus DecodetGPRRegisterClass(MCInst &Inst, unsigned RegNo, static DecodeStatus DecodetGPRRegisterClass(MCInst &Inst, unsigned RegNo,
uint64_t Address, const void *Decoder); uint64_t Address, const void *Decoder);
static DecodeStatus DecodetcGPRRegisterClass(MCInst &Inst, unsigned RegNo, static DecodeStatus DecodetcGPRRegisterClass(MCInst &Inst, unsigned RegNo,
@ -920,6 +923,21 @@ DecodeGPRnopcRegisterClass(MCInst &Inst, unsigned RegNo,
return S; return S;
} }
static DecodeStatus
DecodeGPRwithAPSRRegisterClass(MCInst &Inst, unsigned RegNo,
uint64_t Address, const void *Decoder) {
DecodeStatus S = MCDisassembler::Success;
if (RegNo == 15)
{
Inst.addOperand(MCOperand::CreateReg(ARM::APSR_NZCV));
return MCDisassembler::Success;
}
Check(S, DecodeGPRRegisterClass(Inst, RegNo, Address, Decoder));
return S;
}
static DecodeStatus DecodetGPRRegisterClass(MCInst &Inst, unsigned RegNo, static DecodeStatus DecodetGPRRegisterClass(MCInst &Inst, unsigned RegNo,
uint64_t Address, const void *Decoder) { uint64_t Address, const void *Decoder) {
if (RegNo > 7) if (RegNo > 7)

View File

@ -1062,10 +1062,18 @@ Lforward:
@ MRC/MRC2 @ MRC/MRC2
@------------------------------------------------------------------------------ @------------------------------------------------------------------------------
mrc p14, #0, r1, c1, c2, #4 mrc p14, #0, r1, c1, c2, #4
mrc p15, #7, apsr_nzcv, c15, c6, #6
mrc p15, #7, pc, c15, c6, #6
mrc2 p14, #0, r1, c1, c2, #4 mrc2 p14, #0, r1, c1, c2, #4
mrc2 p10, #7, apsr_nzcv, c15, c0, #1
mrc2 p10, #7, pc, c15, c0, #1
@ CHECK: mrc p14, #0, r1, c1, c2, #4 @ encoding: [0x92,0x1e,0x11,0xee] @ CHECK: mrc p14, #0, r1, c1, c2, #4 @ encoding: [0x92,0x1e,0x11,0xee]
@ CHECK: mrc2 p14, #0, r1, c1, c2, #4 @ encoding: [0x92,0x1e,0x11,0xfe] @ CHECK: mrc p15, #7, apsr_nzcv, c15, c6, #6 @ encoding: [0xd6,0xff,0xff,0xee]
@ CHECK: mrc p15, #7, pc, c15, c6, #6 @ encoding: [0xd6,0xff,0xff,0xee]
@ CHECK: mrc2 p14, #0, r1, c1, c2, #4 @ encoding: [0x92,0x1e,0x11,0xfe]
@ CHECK: mrc2 p10, #7, apsr_nzcv, c15, c0, #1 @ encoding: [0x30,0xfa,0xff,0xfe]
@ CHECK: mrc2 p10, #7, pc, c15, c0, #1 @ encoding: [0x30,0xfa,0xff,0xfe]
@------------------------------------------------------------------------------ @------------------------------------------------------------------------------
@ MRRC/MRRC2 @ MRRC/MRRC2

View File

@ -757,10 +757,14 @@
# MRC/MRC2 # MRC/MRC2
#------------------------------------------------------------------------------ #------------------------------------------------------------------------------
# CHECK: mrc p14, #0, r1, c1, c2, #4 # CHECK: mrc p14, #0, r1, c1, c2, #4
# CHECK: mrc p15, #7, apsr_nzcv, c15, c6, #6
# CHECK: mrc2 p14, #0, r1, c1, c2, #4 # CHECK: mrc2 p14, #0, r1, c1, c2, #4
# CHECK: mrc2 p9, #7, apsr_nzcv, c15, c0, #1
0x92 0x1e 0x11 0xee 0x92 0x1e 0x11 0xee
0xd6 0xff 0xff 0xee
0x92 0x1e 0x11 0xfe 0x92 0x1e 0x11 0xfe
0x30 0xf9 0xff 0xfe
#------------------------------------------------------------------------------ #------------------------------------------------------------------------------
# MRRC/MRRC2 # MRRC/MRRC2