forked from OSchip/llvm-project
[mips][microMIPS] Implement LB, LBE, LBU and LBUE instructions
Differential Revision: http://reviews.llvm.org/D11633 llvm-svn: 250511
This commit is contained in:
parent
1487a3de40
commit
3c88fbd367
|
@ -246,6 +246,16 @@ static DecodeStatus DecodeMemEVA(MCInst &Inst,
|
|||
uint64_t Address,
|
||||
const void *Decoder);
|
||||
|
||||
static DecodeStatus DecodeLoadByte9(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
const void *Decoder);
|
||||
|
||||
static DecodeStatus DecodeLoadByte15(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
const void *Decoder);
|
||||
|
||||
static DecodeStatus DecodeCacheOp(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
|
@ -1153,6 +1163,42 @@ static DecodeStatus DecodeMemEVA(MCInst &Inst,
|
|||
return MCDisassembler::Success;
|
||||
}
|
||||
|
||||
static DecodeStatus DecodeLoadByte9(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
const void *Decoder) {
|
||||
int Offset = SignExtend32<9>(Insn & 0x1ff);
|
||||
unsigned Base = fieldFromInstruction(Insn, 16, 5);
|
||||
unsigned Reg = fieldFromInstruction(Insn, 21, 5);
|
||||
|
||||
Base = getReg(Decoder, Mips::GPR32RegClassID, Base);
|
||||
Reg = getReg(Decoder, Mips::GPR32RegClassID, Reg);
|
||||
|
||||
Inst.addOperand(MCOperand::createReg(Reg));
|
||||
Inst.addOperand(MCOperand::createReg(Base));
|
||||
Inst.addOperand(MCOperand::createImm(Offset));
|
||||
|
||||
return MCDisassembler::Success;
|
||||
}
|
||||
|
||||
static DecodeStatus DecodeLoadByte15(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
const void *Decoder) {
|
||||
int Offset = SignExtend32<16>(Insn & 0xffff);
|
||||
unsigned Base = fieldFromInstruction(Insn, 16, 5);
|
||||
unsigned Reg = fieldFromInstruction(Insn, 21, 5);
|
||||
|
||||
Base = getReg(Decoder, Mips::GPR32RegClassID, Base);
|
||||
Reg = getReg(Decoder, Mips::GPR32RegClassID, Reg);
|
||||
|
||||
Inst.addOperand(MCOperand::createReg(Reg));
|
||||
Inst.addOperand(MCOperand::createReg(Base));
|
||||
Inst.addOperand(MCOperand::createImm(Offset));
|
||||
|
||||
return MCDisassembler::Success;
|
||||
}
|
||||
|
||||
static DecodeStatus DecodeCacheOp(MCInst &Inst,
|
||||
unsigned Insn,
|
||||
uint64_t Address,
|
||||
|
|
|
@ -773,7 +773,7 @@ getMemEncodingMMGPImm7Lsl2(const MCInst &MI, unsigned OpNo,
|
|||
return OffBits & 0x7F;
|
||||
}
|
||||
|
||||
unsigned MipsMCCodeEmitter::
|
||||
unsigned MipsMCCodeEmitter::
|
||||
getMemEncodingMMImm9(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
const MCSubtargetInfo &STI) const {
|
||||
|
@ -809,6 +809,19 @@ getMemEncodingMMImm12(const MCInst &MI, unsigned OpNo,
|
|||
return (OffBits & 0x0FFF) | RegBits;
|
||||
}
|
||||
|
||||
unsigned MipsMCCodeEmitter::
|
||||
getMemEncodingMMImm16(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
const MCSubtargetInfo &STI) const {
|
||||
// Base register is encoded in bits 20-16, offset is encoded in bits 15-0.
|
||||
assert(MI.getOperand(OpNo).isReg());
|
||||
unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups,
|
||||
STI) << 16;
|
||||
unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI);
|
||||
|
||||
return (OffBits & 0xFFFF) | RegBits;
|
||||
}
|
||||
|
||||
unsigned MipsMCCodeEmitter::
|
||||
getMemEncodingMMImm4sp(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
|
|
|
@ -178,6 +178,9 @@ public:
|
|||
unsigned getMemEncodingMMImm12(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
const MCSubtargetInfo &STI) const;
|
||||
unsigned getMemEncodingMMImm16(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
const MCSubtargetInfo &STI) const;
|
||||
unsigned getMemEncodingMMImm4sp(const MCInst &MI, unsigned OpNo,
|
||||
SmallVectorImpl<MCFixup> &Fixups,
|
||||
const MCSubtargetInfo &STI) const;
|
||||
|
|
|
@ -133,6 +133,48 @@ class POOL32C_ST_EVA_FM_MMR6<bits<6> op, bits<3> funct> : MipsR6Inst {
|
|||
let Inst{8-0} = offset;
|
||||
}
|
||||
|
||||
class LB32_FM_MMR6 : MipsR6Inst {
|
||||
bits<21> addr;
|
||||
bits<5> rt;
|
||||
bits<5> base = addr{20-16};
|
||||
bits<16> offset = addr{15-0};
|
||||
|
||||
bits<32> Inst;
|
||||
|
||||
let Inst{31-26} = 0b000111;
|
||||
let Inst{25-21} = rt;
|
||||
let Inst{20-16} = base;
|
||||
let Inst{15-0} = offset;
|
||||
}
|
||||
|
||||
class LBU32_FM_MMR6 : MipsR6Inst {
|
||||
bits<21> addr;
|
||||
bits<5> rt;
|
||||
bits<5> base = addr{20-16};
|
||||
bits<16> offset = addr{15-0};
|
||||
|
||||
bits<32> Inst;
|
||||
|
||||
let Inst{31-26} = 0b000101;
|
||||
let Inst{25-21} = rt;
|
||||
let Inst{20-16} = base;
|
||||
let Inst{15-0} = offset;
|
||||
}
|
||||
|
||||
class POOL32C_LB_LBU_FM_MMR6<bits<3> funct> : MipsR6Inst {
|
||||
bits<21> addr;
|
||||
bits<5> rt;
|
||||
|
||||
bits<32> Inst;
|
||||
|
||||
let Inst{31-26} = 0b011000;
|
||||
let Inst{25-21} = rt;
|
||||
let Inst{20-16} = addr{20-16};
|
||||
let Inst{15-12} = 0b0110;
|
||||
let Inst{11-9} = funct;
|
||||
let Inst{8-0} = addr{8-0};
|
||||
}
|
||||
|
||||
class SIGN_EXTEND_FM_MMR6<string instr_asm, bits<10> funct>
|
||||
: MMR6Arch<instr_asm> {
|
||||
bits<5> rd;
|
||||
|
|
|
@ -78,6 +78,10 @@ class PREFE_MMR6_ENC : POOL32C_ST_EVA_FM_MMR6<0b011000, 0b010>;
|
|||
class CACHEE_MMR6_ENC : POOL32C_ST_EVA_FM_MMR6<0b011000, 0b011>;
|
||||
class WRPGPR_MMR6_ENC : POOL32A_WRPGPR_WSBH_FM_MMR6<0x3c5>;
|
||||
class WSBH_MMR6_ENC : POOL32A_WRPGPR_WSBH_FM_MMR6<0x1ec>;
|
||||
class LB_MMR6_ENC : LB32_FM_MMR6;
|
||||
class LBU_MMR6_ENC : LBU32_FM_MMR6;
|
||||
class LBE_MMR6_ENC : POOL32C_LB_LBU_FM_MMR6<0b100>;
|
||||
class LBUE_MMR6_ENC : POOL32C_LB_LBU_FM_MMR6<0b000>;
|
||||
class XOR_MMR6_ENC : ARITH_FM_MMR6<"xor", 0x310>;
|
||||
class XORI_MMR6_ENC : ADDI_FM_MMR6<"xori", 0x1c>;
|
||||
class ABS_S_MMR6_ENC : POOL32F_ABS_FM_MMR6<"abs.s", 0, 0b0001101>;
|
||||
|
@ -285,6 +289,25 @@ class PREFE_CACHEE_MMR6_DESC_BASE<string instr_asm, Operand MemOpnd,
|
|||
class PREFE_MMR6_DESC : PREFE_CACHEE_MMR6_DESC_BASE<"prefe", mem_mm_9, GPR32Opnd>;
|
||||
class CACHEE_MMR6_DESC : PREFE_CACHEE_MMR6_DESC_BASE<"cachee", mem_mm_9, GPR32Opnd>;
|
||||
|
||||
class LB_LBU_MMR6_DESC_BASE<string instr_asm, Operand MemOpnd,
|
||||
RegisterOperand GPROpnd> : MMR6Arch<instr_asm> {
|
||||
dag OutOperandList = (outs GPROpnd:$rt);
|
||||
dag InOperandList = (ins MemOpnd:$addr);
|
||||
string AsmString = !strconcat(instr_asm, "\t$rt, $addr");
|
||||
string DecoderMethod = "DecodeLoadByte15";
|
||||
bit mayLoad = 1;
|
||||
}
|
||||
class LB_MMR6_DESC : LB_LBU_MMR6_DESC_BASE<"lb", mem_mm_16, GPR32Opnd>;
|
||||
class LBU_MMR6_DESC : LB_LBU_MMR6_DESC_BASE<"lbu", mem_mm_16, GPR32Opnd>;
|
||||
|
||||
class LBE_LBUE_MMR6_DESC_BASE<string instr_asm, Operand MemOpnd,
|
||||
RegisterOperand GPROpnd>
|
||||
: LB_LBU_MMR6_DESC_BASE<instr_asm, MemOpnd, GPROpnd> {
|
||||
let DecoderMethod = "DecodeLoadByte9";
|
||||
}
|
||||
class LBE_MMR6_DESC : LBE_LBUE_MMR6_DESC_BASE<"lbe", mem_mm_9, GPR32Opnd>;
|
||||
class LBUE_MMR6_DESC : LBE_LBUE_MMR6_DESC_BASE<"lbue", mem_mm_9, GPR32Opnd>;
|
||||
|
||||
class CLO_CLZ_MMR6_DESC_BASE<string instr_asm, RegisterOperand GPROpnd>
|
||||
: MMR6Arch<instr_asm> {
|
||||
dag OutOperandList = (outs GPROpnd:$rt);
|
||||
|
@ -830,6 +853,10 @@ def CACHEE_MMR6 : StdMMR6Rel, CACHEE_MMR6_ENC, CACHEE_MMR6_DESC,
|
|||
def WRPGPR_MMR6 : StdMMR6Rel, WRPGPR_MMR6_ENC, WRPGPR_MMR6_DESC,
|
||||
ISA_MICROMIPS32R6;
|
||||
def WSBH_MMR6 : StdMMR6Rel, WSBH_MMR6_ENC, WSBH_MMR6_DESC, ISA_MICROMIPS32R6;
|
||||
def LB_MMR6 : R6MMR6Rel, LB_MMR6_ENC, LB_MMR6_DESC, ISA_MICROMIPS32R6;
|
||||
def LBU_MMR6 : R6MMR6Rel, LBU_MMR6_ENC, LBU_MMR6_DESC, ISA_MICROMIPS32R6;
|
||||
def LBE_MMR6 : R6MMR6Rel, LBE_MMR6_ENC, LBE_MMR6_DESC, ISA_MICROMIPS32R6;
|
||||
def LBUE_MMR6 : R6MMR6Rel, LBUE_MMR6_ENC, LBUE_MMR6_DESC, ISA_MICROMIPS32R6;
|
||||
def XOR_MMR6 : StdMMR6Rel, XOR_MMR6_DESC, XOR_MMR6_ENC, ISA_MICROMIPS32R6;
|
||||
def XORI_MMR6 : StdMMR6Rel, XORI_MMR6_DESC, XORI_MMR6_ENC, ISA_MICROMIPS32R6;
|
||||
let DecoderMethod = "DecodeMemMMImm16" in {
|
||||
|
|
|
@ -130,6 +130,14 @@ def mem_mm_12 : Operand<i32> {
|
|||
let OperandType = "OPERAND_MEMORY";
|
||||
}
|
||||
|
||||
def mem_mm_16 : Operand<i32> {
|
||||
let PrintMethod = "printMemOperand";
|
||||
let MIOperandInfo = (ops GPR32, simm16);
|
||||
let EncoderMethod = "getMemEncodingMMImm16";
|
||||
let ParserMatchClass = MipsMemAsmOperand;
|
||||
let OperandType = "OPERAND_MEMORY";
|
||||
}
|
||||
|
||||
def MipsMemUimm4AsmOperand : AsmOperandClass {
|
||||
let Name = "MemOffsetUimm4";
|
||||
let SuperClasses = [MipsMemAsmOperand];
|
||||
|
|
|
@ -214,3 +214,7 @@
|
|||
0x46 0x3b # CHECK: sdbbp16 8
|
||||
0x04 0x3b # CHECK: subu16 $5, $16, $3
|
||||
0x44 0xd8 # CHECK: xor16 $17, $5
|
||||
0x1c 0x85 0x00 0x08 # CHECK: lb $4, 8($5)
|
||||
0x14 0x85 0x00 0x08 # CHECK: lbu $4, 8($5)
|
||||
0x60 0x85 0x68 0x08 # CHECK: lbe $4, 8($5)
|
||||
0x60 0x85 0x60 0x08 # CHECK: lbue $4, 8($5)
|
||||
|
|
|
@ -204,3 +204,7 @@
|
|||
sdbbp16 8 # CHECK: sdbbp16 8 # encoding: [0x46,0x3b]
|
||||
subu16 $5, $16, $3 # CHECK: subu16 $5, $16, $3 # encoding: [0x04,0x3b]
|
||||
xor16 $17, $5 # CHECK: xor16 $17, $5 # encoding: [0x44,0xd8]
|
||||
lb $4, 8($5) # CHECK: lb $4, 8($5) # encoding: [0x1c,0x85,0x00,0x08]
|
||||
lbu $4, 8($5) # CHECK: lbu $4, 8($5) # encoding: [0x14,0x85,0x00,0x08]
|
||||
lbe $4, 8($5) # CHECK: lbe $4, 8($5) # encoding: [0x60,0x85,0x68,0x08]
|
||||
lbue $4, 8($5) # CHECK: lbue $4, 8($5) # encoding: [0x60,0x85,0x60,0x08]
|
||||
|
|
Loading…
Reference in New Issue