mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-24 03:33:20 +01:00
Fix broken encodings for the Thumb2 LDRD/STRD instructions.
llvm-svn: 136942
This commit is contained in:
parent
3956112276
commit
11e2000c8c
@ -1151,6 +1151,27 @@ class T2Ii8s4<bit P, bit W, bit isLoad, dag oops, dag iops, InstrItinClass itin,
|
||||
let Inst{7-0} = addr{7-0};
|
||||
}
|
||||
|
||||
class T2Ii8s4Tied<bit P, bit W, bit isLoad, dag oops, dag iops, InstrItinClass itin,
|
||||
string opc, string asm, list<dag> pattern>
|
||||
: Thumb2I<oops, iops, AddrModeT2_i8s4, 4, itin, opc, asm, "$base = $wb",
|
||||
pattern> {
|
||||
bits<4> Rt;
|
||||
bits<4> Rt2;
|
||||
bits<4> base;
|
||||
bits<9> imm;
|
||||
let Inst{31-25} = 0b1110100;
|
||||
let Inst{24} = P;
|
||||
let Inst{23} = imm{8};
|
||||
let Inst{22} = 1;
|
||||
let Inst{21} = W;
|
||||
let Inst{20} = isLoad;
|
||||
let Inst{19-16} = base{3-0};
|
||||
let Inst{15-12} = Rt{3-0};
|
||||
let Inst{11-8} = Rt2{3-0};
|
||||
let Inst{7-0} = imm{7-0};
|
||||
}
|
||||
|
||||
|
||||
class T2sI<dag oops, dag iops, InstrItinClass itin,
|
||||
string opc, string asm, list<dag> pattern>
|
||||
: Thumb2sI<oops, iops, AddrModeNone, 4, itin, opc, asm, "", pattern>;
|
||||
|
@ -141,6 +141,7 @@ def t2addrmode_imm8s4 : Operand<i32> {
|
||||
|
||||
def t2am_imm8s4_offset : Operand<i32> {
|
||||
let PrintMethod = "printT2AddrModeImm8s4OffsetOperand";
|
||||
let DecoderMethod = "DecodeT2Imm8S4";
|
||||
}
|
||||
|
||||
// t2addrmode_so_reg := reg + (reg << imm2)
|
||||
@ -1354,19 +1355,21 @@ def t2STRHT : T2IstT<0b01, "strht", IIC_iStore_bh_i>;
|
||||
// ldrd / strd pre / post variants
|
||||
// For disassembly only.
|
||||
|
||||
def t2LDRD_PRE : T2Ii8s4<1, 1, 1, (outs rGPR:$Rt, rGPR:$Rt2),
|
||||
def t2LDRD_PRE : T2Ii8s4Tied<1, 1, 1,
|
||||
(outs rGPR:$Rt, rGPR:$Rt2, GPR:$wb),
|
||||
(ins GPR:$base, t2am_imm8s4_offset:$imm), IIC_iLoad_d_ru,
|
||||
"ldrd", "\t$Rt, $Rt2, [$base, $imm]!", []>;
|
||||
|
||||
def t2LDRD_POST : T2Ii8s4<0, 1, 1, (outs rGPR:$Rt, rGPR:$Rt2),
|
||||
def t2LDRD_POST : T2Ii8s4Tied<0, 1, 1,
|
||||
(outs rGPR:$Rt, rGPR:$Rt2, GPR:$wb),
|
||||
(ins GPR:$base, t2am_imm8s4_offset:$imm), IIC_iLoad_d_ru,
|
||||
"ldrd", "\t$Rt, $Rt2, [$base], $imm", []>;
|
||||
|
||||
def t2STRD_PRE : T2Ii8s4<1, 1, 0, (outs),
|
||||
def t2STRD_PRE : T2Ii8s4Tied<1, 1, 0, (outs GPR:$wb),
|
||||
(ins rGPR:$Rt, rGPR:$Rt2, GPR:$base, t2am_imm8s4_offset:$imm),
|
||||
IIC_iStore_d_ru, "strd", "\t$Rt, $Rt2, [$base, $imm]!", []>;
|
||||
|
||||
def t2STRD_POST : T2Ii8s4<0, 1, 0, (outs),
|
||||
def t2STRD_POST : T2Ii8s4Tied<0, 1, 0, (outs GPR:$wb),
|
||||
(ins rGPR:$Rt, rGPR:$Rt2, GPR:$base, t2am_imm8s4_offset:$imm),
|
||||
IIC_iStore_d_ru, "strd", "\t$Rt, $Rt2, [$base], $imm", []>;
|
||||
|
||||
|
@ -1318,13 +1318,6 @@ static bool DisassembleThumb2LdStDual(MCInst &MI, unsigned Opcode,
|
||||
const MCOperandInfo *OpInfo = ARMInsts[Opcode].OpInfo;
|
||||
if (!OpInfo) return false;
|
||||
|
||||
assert(NumOps >= 4
|
||||
&& OpInfo[0].RegClass > 0
|
||||
&& OpInfo[0].RegClass == OpInfo[1].RegClass
|
||||
&& OpInfo[2].RegClass > 0
|
||||
&& OpInfo[3].RegClass < 0
|
||||
&& "Expect >= 4 operands and first 3 as reg operands");
|
||||
|
||||
// Thumnb allows for specifying Rt and Rt2, unlike ARM (which has Rt2==Rt+1).
|
||||
unsigned Rt = decodeRd(insn);
|
||||
unsigned Rt2 = decodeRs(insn);
|
||||
@ -1357,20 +1350,32 @@ static bool DisassembleThumb2LdStDual(MCInst &MI, unsigned Opcode,
|
||||
// Add the <Rt> <Rt2> operands.
|
||||
unsigned RegClassPair = OpInfo[0].RegClass;
|
||||
unsigned RegClassBase = OpInfo[2].RegClass;
|
||||
|
||||
|
||||
MI.addOperand(MCOperand::CreateReg(getRegisterEnum(B, RegClassPair,
|
||||
decodeRd(insn))));
|
||||
MI.addOperand(MCOperand::CreateReg(getRegisterEnum(B, RegClassPair,
|
||||
decodeRs(insn))));
|
||||
MI.addOperand(MCOperand::CreateReg(getRegisterEnum(B, RegClassBase,
|
||||
decodeRn(insn))));
|
||||
unsigned Added = 4;
|
||||
switch (MI.getOpcode()) {
|
||||
case ARM::t2LDRD_PRE:
|
||||
case ARM::t2LDRD_POST:
|
||||
case ARM::t2STRD_PRE:
|
||||
case ARM::t2STRD_POST:
|
||||
MI.addOperand(MCOperand::CreateReg(getRegisterEnum(B, RegClassBase,
|
||||
decodeRn(insn))));
|
||||
Added = 5;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// Finally add (+/-)imm8*4, depending on the U bit.
|
||||
int Offset = getImm8(insn) * 4;
|
||||
if (getUBit(insn) == 0)
|
||||
Offset = -Offset;
|
||||
MI.addOperand(MCOperand::CreateImm(Offset));
|
||||
NumOpsAdded = 4;
|
||||
NumOpsAdded = Added;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user