forked from OSchip/llvm-project
[mips][microMIPS] Implement DINSU, DINSM, DINS instructions
Differential Revision: http://reviews.llvm.org/D16181 llvm-svn: 261860
This commit is contained in:
parent
31a2f8f9f5
commit
46458d0bcc
|
@ -1032,6 +1032,10 @@ public:
|
|||
template <unsigned Bits> bool isConstantSImm() const {
|
||||
return isConstantImm() && isInt<Bits>(getConstantImm());
|
||||
}
|
||||
template <unsigned Bottom, unsigned Top> bool isConstantUImmRange() const {
|
||||
return isConstantImm() && getConstantImm() >= Bottom &&
|
||||
getConstantImm() <= Top;
|
||||
}
|
||||
bool isToken() const override {
|
||||
// Note: It's not possible to pretend that other operand kinds are tokens.
|
||||
// The matcher emitter checks tokens first.
|
||||
|
@ -3749,6 +3753,9 @@ bool MipsAsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
|
|||
case Match_UImm5_Lsl2:
|
||||
return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo),
|
||||
"expected both 7-bit unsigned immediate and multiple of 4");
|
||||
case Match_UImmRange2_64:
|
||||
return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo),
|
||||
"expected immediate in range 2 .. 64");
|
||||
case Match_UImm6_0:
|
||||
return Error(RefineErrorLoc(IDLoc, Operands, ErrorInfo),
|
||||
"expected 6-bit unsigned immediate");
|
||||
|
|
|
@ -28,6 +28,9 @@ class DDIV_MM64R6_ENC : POOL32A_DIVMOD_FM_MMR6<"ddiv", 0b100011000>;
|
|||
class DMOD_MM64R6_ENC : POOL32A_DIVMOD_FM_MMR6<"dmod", 0b101011000>;
|
||||
class DDIVU_MM64R6_ENC : POOL32A_DIVMOD_FM_MMR6<"ddivu", 0b110011000>;
|
||||
class DMODU_MM64R6_ENC : POOL32A_DIVMOD_FM_MMR6<"dmodu", 0b111011000>;
|
||||
class DINSU_MM64R6_ENC : POOL32S_EXTBITS_FM_MMR6<0b110100>;
|
||||
class DINSM_MM64R6_ENC : POOL32S_EXTBITS_FM_MMR6<0b000100>;
|
||||
class DINS_MM64R6_ENC : POOL32S_EXTBITS_FM_MMR6<0b001100>;
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
|
@ -90,6 +93,12 @@ class DMOD_MM64R6_DESC : ArithLogicR<"dmod", GPR32Opnd>;
|
|||
class DDIVU_MM64R6_DESC : ArithLogicR<"ddivu", GPR32Opnd>;
|
||||
class DMODU_MM64R6_DESC : ArithLogicR<"dmodu", GPR32Opnd>;
|
||||
|
||||
class DINSU_MM64R6_DESC : InsBase<"dinsu", GPR64Opnd, uimm5_plus32,
|
||||
uimm5_inssize_plus1, MipsIns>;
|
||||
class DINSM_MM64R6_DESC : InsBase<"dinsm", GPR64Opnd, uimm5, uimm_range_2_64>;
|
||||
class DINS_MM64R6_DESC : InsBase<"dins", GPR64Opnd, uimm5, uimm5_inssize_plus1,
|
||||
MipsIns>;
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// Instruction Definitions
|
||||
|
@ -116,4 +125,10 @@ let DecoderNamespace = "MicroMipsR6" in {
|
|||
ISA_MICROMIPS64R6;
|
||||
def DMODU_MM64R6 : R6MMR6Rel, DMODU_MM64R6_DESC, DMODU_MM64R6_ENC,
|
||||
ISA_MICROMIPS64R6;
|
||||
def DINSU_MM64R6: R6MMR6Rel, DINSU_MM64R6_DESC, DINSU_MM64R6_ENC,
|
||||
ISA_MICROMIPS64R6;
|
||||
def DINSM_MM64R6: R6MMR6Rel, DINSM_MM64R6_DESC, DINSM_MM64R6_ENC,
|
||||
ISA_MICROMIPS64R6;
|
||||
def DINS_MM64R6: R6MMR6Rel, DINS_MM64R6_DESC, DINS_MM64R6_ENC,
|
||||
ISA_MICROMIPS64R6;
|
||||
}
|
||||
|
|
|
@ -847,8 +847,8 @@ let DecoderNamespace = "MicroMips", Predicates = [InMicroMips] in {
|
|||
// TODO: Add '0 < pos+size <= 32' constraint check to ext instruction
|
||||
def EXT_MM : MMRel, ExtBase<"ext", GPR32Opnd, uimm5, uimm5_plus1,
|
||||
MipsExt>, EXT_FM_MM<0x2c>;
|
||||
def INS_MM : MMRel, InsBase<"ins", GPR32Opnd, uimm5, MipsIns>,
|
||||
EXT_FM_MM<0x0c>;
|
||||
def INS_MM : MMRel, InsBase<"ins", GPR32Opnd, uimm5, uimm5_inssize_plus1,
|
||||
MipsIns>, EXT_FM_MM<0x0c>;
|
||||
|
||||
/// Jump Instructions
|
||||
let DecoderMethod = "DecodeJumpTargetMM" in {
|
||||
|
|
|
@ -277,12 +277,14 @@ let AdditionalPredicates = [NotInMicroMips] in {
|
|||
EXT_FM<1>;
|
||||
def DEXTU : ExtBase<"dextu", GPR64Opnd, uimm5_plus32, uimm5_plus1,
|
||||
MipsExt>, EXT_FM<2>;
|
||||
def DINS : InsBase<"dins", GPR64Opnd, uimm6, uimm5_inssize_plus1, MipsIns>,
|
||||
EXT_FM<7>;
|
||||
def DINSU : InsBase<"dinsu", GPR64Opnd, uimm5_plus32, uimm5_inssize_plus1>,
|
||||
EXT_FM<6>;
|
||||
def DINSM : InsBase<"dinsm", GPR64Opnd, uimm5, uimm5_inssize_plus1>,
|
||||
EXT_FM<5>;
|
||||
}
|
||||
|
||||
def DINS : InsBase<"dins", GPR64Opnd, uimm6, MipsIns>, EXT_FM<7>;
|
||||
def DINSU : InsBase<"dinsu", GPR64Opnd, uimm5_plus32>, EXT_FM<6>;
|
||||
def DINSM : InsBase<"dinsm", GPR64Opnd, uimm5>, EXT_FM<5>;
|
||||
|
||||
let isCodeGenOnly = 1, rs = 0, shamt = 0 in {
|
||||
def DSLL64_32 : FR<0x00, 0x3c, (outs GPR64:$rd), (ins GPR32:$rt),
|
||||
"dsll\t$rd, $rt, 32", [], II_DSLL>;
|
||||
|
|
|
@ -403,6 +403,16 @@ class ConstantUImmAsmOperandClass<int Bits, list<AsmOperandClass> Supers = [],
|
|||
let DiagnosticType = "UImm" # Bits # "_" # Offset;
|
||||
}
|
||||
|
||||
class ConstantUImmRangeAsmOperandClass<int Bottom, int Top,
|
||||
list<AsmOperandClass> Supers = []>
|
||||
: AsmOperandClass {
|
||||
let Name = "ConstantUImmRange" # Bottom # "_" # Top;
|
||||
let RenderMethod = "addImmOperands";
|
||||
let PredicateMethod = "isConstantUImmRange<" # Bottom # ", " # Top # ">";
|
||||
let SuperClasses = Supers;
|
||||
let DiagnosticType = "UImmRange" # Bottom # "_" # Top;
|
||||
}
|
||||
|
||||
class UImmAsmOperandClass<int Bits, list<AsmOperandClass> Supers = []>
|
||||
: AsmOperandClass {
|
||||
let Name = "UImm" # Bits;
|
||||
|
@ -432,6 +442,8 @@ def ConstantSImm6AsmOperandClass
|
|||
: ConstantSImmAsmOperandClass<6, [ConstantUImm7AsmOperandClass]>;
|
||||
def ConstantUImm5Plus1AsmOperandClass
|
||||
: ConstantUImmAsmOperandClass<5, [ConstantUImm6AsmOperandClass], 1>;
|
||||
def ConstantUImm5_Range2_64AsmOperandClass
|
||||
: ConstantUImmRangeAsmOperandClass<2, 64, [ConstantUImm6AsmOperandClass]>;
|
||||
def ConstantUImm5Plus32AsmOperandClass
|
||||
: ConstantUImmAsmOperandClass<5, [ConstantUImm6AsmOperandClass], 32>;
|
||||
def ConstantUImm5Plus33AsmOperandClass
|
||||
|
@ -542,6 +554,14 @@ def uimmz : Operand<i32> {
|
|||
let ParserMatchClass = ConstantImmzAsmOperandClass;
|
||||
}
|
||||
|
||||
// size operand of ins instruction
|
||||
def uimm_range_2_64 : Operand<i32> {
|
||||
let PrintMethod = "printUnsignedImm";
|
||||
let EncoderMethod = "getSizeInsEncoding";
|
||||
let DecoderMethod = "DecodeInsSize";
|
||||
let ParserMatchClass = ConstantUImm5_Range2_64AsmOperandClass;
|
||||
}
|
||||
|
||||
// Unsigned Operands
|
||||
foreach I = {1, 2, 3, 4, 5, 6, 7, 8, 10} in
|
||||
def uimm # I : Operand<i32> {
|
||||
|
@ -576,6 +596,13 @@ def uimm5_plus33 : Operand<i32> {
|
|||
let ParserMatchClass = ConstantUImm5Plus33AsmOperandClass;
|
||||
}
|
||||
|
||||
def uimm5_inssize_plus1 : Operand<i32> {
|
||||
let PrintMethod = "printUnsignedImm";
|
||||
let ParserMatchClass = ConstantUImm5Plus1AsmOperandClass;
|
||||
let EncoderMethod = "getSizeInsEncoding";
|
||||
let DecoderMethod = "DecodeInsSize";
|
||||
}
|
||||
|
||||
def uimm5_plus32_normalize : Operand<i32> {
|
||||
let PrintMethod = "printUnsignedImm";
|
||||
let ParserMatchClass = ConstantUImm5Plus32NormalizeAsmOperandClass;
|
||||
|
@ -1253,8 +1280,8 @@ class ExtBase<string opstr, RegisterOperand RO, Operand PosOpnd,
|
|||
FrmR, opstr>, ISA_MIPS32R2;
|
||||
|
||||
class InsBase<string opstr, RegisterOperand RO, Operand PosOpnd,
|
||||
SDPatternOperator Op = null_frag>:
|
||||
InstSE<(outs RO:$rt), (ins RO:$rs, PosOpnd:$pos, size_ins:$size, RO:$src),
|
||||
Operand SizeOpnd, SDPatternOperator Op = null_frag>:
|
||||
InstSE<(outs RO:$rt), (ins RO:$rs, PosOpnd:$pos, SizeOpnd:$size, RO:$src),
|
||||
!strconcat(opstr, " $rt, $rs, $pos, $size"),
|
||||
[(set RO:$rt, (Op RO:$rs, imm:$pos, imm:$size, RO:$src))],
|
||||
II_INS, FrmR, opstr>, ISA_MIPS32R2 {
|
||||
|
@ -1738,7 +1765,8 @@ def RDHWR : MMRel, ReadHardware<GPR32Opnd, HWRegsOpnd>, RDHWR_FM;
|
|||
// TODO: Add '0 < pos+size <= 32' constraint check to ext instruction
|
||||
def EXT : MMRel, ExtBase<"ext", GPR32Opnd, uimm5, uimm5_plus1, MipsExt>,
|
||||
EXT_FM<0>;
|
||||
def INS : MMRel, InsBase<"ins", GPR32Opnd, uimm5, MipsIns>, EXT_FM<4>;
|
||||
def INS : MMRel, InsBase<"ins", GPR32Opnd, uimm5, uimm5_inssize_plus1, MipsIns>,
|
||||
EXT_FM<4>;
|
||||
|
||||
/// Move Control Registers From/To CPU Registers
|
||||
def MFC0 : MFC3OP<"mfc0", GPR32Opnd, COP0Opnd>, MFC3OP_FM<0x10, 0>, ISA_MIPS32;
|
||||
|
|
|
@ -171,3 +171,6 @@
|
|||
0x00 0x0f 0x47 0x7c # CHECK: di $15
|
||||
0x00 0x00 0x43 0x7c # CHECK: tlbinv
|
||||
0x00 0x00 0x53 0x7c # CHECK: tlbinvf
|
||||
0x58 0x82 0x20 0x34 # CHECK: dinsu $4, $2, 0, 5
|
||||
0x58 0x82 0x38 0xc4 # CHECK: dinsm $4, $2, 3, 5
|
||||
0x58 0x82 0x38 0xcc # CHECK: dins $4, $2, 3, 5
|
||||
|
|
|
@ -13,3 +13,7 @@ foo:
|
|||
bbit1 $19, 64, foo # CHECK: :[[@LINE]]:16: error: expected 6-bit unsigned immediate
|
||||
bbit132 $19, -1, foo # CHECK: :[[@LINE]]:18: error: expected 5-bit unsigned immediate
|
||||
bbit132 $19, 32, foo # CHECK: :[[@LINE]]:18: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, -1, 1 # CHECK: :[[@LINE]]:17: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, 32, 1 # CHECK: :[[@LINE]]:17: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, 0, -1 # CHECK: :[[@LINE]]:20: error: expected immediate in range 1 .. 32
|
||||
ins $2, $3, 0, 33 # CHECK: :[[@LINE]]:20: error: expected immediate in range 1 .. 32
|
||||
|
|
|
@ -33,3 +33,7 @@
|
|||
sra $2, $3, 32 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
srl $2, $3, -1 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
srl $2, $3, 32 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, -1, 1 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, 32, 1 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
ins $2, $3, 0, -1 # CHECK: :[[@LINE]]:18: error: expected immediate in range 1 .. 32
|
||||
ins $2, $3, 0, 33 # CHECK: :[[@LINE]]:18: error: expected immediate in range 1 .. 32
|
||||
|
|
|
@ -25,3 +25,5 @@
|
|||
tne $8, $9, $2 # CHECK: :[[@LINE]]:15: error: expected 10-bit unsigned immediate
|
||||
tne $8, $9, -1 # CHECK: :[[@LINE]]:15: error: expected 10-bit unsigned immediate
|
||||
tne $8, $9, 16 # CHECK: :[[@LINE]]:3: error: instruction requires a CPU feature not currently enabled
|
||||
dins $2, $3, -1, 1 # CHECK: :[[@LINE]]:16: error: expected 6-bit unsigned immediate
|
||||
dins $2, $3, 32, 1 # CHECK: :[[@LINE]]:3: error: instruction requires a CPU feature not currently enabled
|
||||
|
|
|
@ -33,13 +33,17 @@
|
|||
dextu $2, $3, 64, 1 # CHECK: :[[@LINE]]:17: error: expected immediate in range 32 .. 63
|
||||
dextu $2, $3, 32, 0 # CHECK: :[[@LINE]]:21: error: expected immediate in range 1 .. 32
|
||||
dextu $2, $3, 32, 33 # CHECK: :[[@LINE]]:21: error: expected immediate in range 1 .. 32
|
||||
# FIXME: Check size on dins*
|
||||
dins $2, $3, -1, 1 # CHECK: :[[@LINE]]:16: error: expected 6-bit unsigned immediate
|
||||
dins $2, $3, 64, 1 # CHECK: :[[@LINE]]:16: error: expected 6-bit unsigned immediate
|
||||
dins $2, $3, 31, 33 # CHECK: :[[@LINE]]:20: error: expected immediate in range 1 .. 32
|
||||
dins $2, $3, 31, 0 # CHECK: :[[@LINE]]:20: error: expected immediate in range 1 .. 32
|
||||
# FIXME: Check '32 <= pos + size <= 64' constraint on dinsm
|
||||
dinsm $2, $3, -1, 1 # CHECK: :[[@LINE]]:17: error: expected 5-bit unsigned immediate
|
||||
dinsm $2, $3, 32, 1 # CHECK: :[[@LINE]]:17: error: expected 5-bit unsigned immediate
|
||||
dinsm $2, $3, 31, 0 # CHECK: :[[@LINE]]:21: error: expected immediate in range 2 .. 64
|
||||
dinsm $2, $3, 31, 65 # CHECK: :[[@LINE]]:21: error: expected immediate in range 2 .. 64
|
||||
dinsu $2, $3, 31, 1 # CHECK: :[[@LINE]]:17: error: expected immediate in range 32 .. 63
|
||||
dinsu $2, $3, 64, 1 # CHECK: :[[@LINE]]:17: error: expected immediate in range 32 .. 63
|
||||
dinsu $2, $3, 63, 0 # CHECK: :[[@LINE]]:21: error: expected immediate in range 1 .. 32
|
||||
dinsu $2, $3, 32, 33 # CHECK: :[[@LINE]]:21: error: expected immediate in range 1 .. 32
|
||||
# FIXME: Check '0 < pos + size <= 32' constraint on ext
|
||||
ext $2, $3, -1, 31 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
ext $2, $3, 32, 31 # CHECK: :[[@LINE]]:15: error: expected 5-bit unsigned immediate
|
||||
|
|
|
@ -156,5 +156,7 @@ a:
|
|||
floor.l.d $f1, $f3 # CHECK: floor.l.d $f1, $f3 # encoding: [0x54,0x23,0x43,0x3b]
|
||||
tlbinv # CHECK: tlbinv # encoding: [0x00,0x00,0x43,0x7c]
|
||||
tlbinvf # CHECK: tlbinvf # encoding: [0x00,0x00,0x53,0x7c]
|
||||
|
||||
dinsu $4, $2, 32, 5 # CHECK: dinsu $4, $2, 32, 5 # encoding: [0x58,0x82,0x20,0x34]
|
||||
dinsm $4, $2, 3, 5 # CHECK: dinsm $4, $2, 3, 5 # encoding: [0x58,0x82,0x38,0xc4]
|
||||
dins $4, $2, 3, 5 # CHECK: dins $4, $2, 3, 5 # encoding: [0x58,0x82,0x38,0xcc]
|
||||
1:
|
||||
|
|
|
@ -23,3 +23,13 @@
|
|||
seb $25,$15 # CHECK: :[[@LINE]]:{{[0-9]+}}: error: instruction requires a CPU feature not currently enabled
|
||||
seh $v1,$12 # CHECK: :[[@LINE]]:{{[0-9]+}}: error: instruction requires a CPU feature not currently enabled
|
||||
wsbh $k1,$9 # CHECK: :[[@LINE]]:{{[0-9]+}}: error: instruction requires a CPU feature not currently enabled
|
||||
dins $2, $3, -1, 1 # CHECK: :[[@LINE]]:22: error: expected 6-bit unsigned immediate
|
||||
dins $2, $3, 64, 1 # CHECK: :[[@LINE]]:22: error: expected 6-bit unsigned immediate
|
||||
dinsm $2, $3, -1, 1 # CHECK: :[[@LINE]]:23: error: expected 5-bit unsigned immediate
|
||||
dinsm $2, $3, 32, 1 # CHECK: :[[@LINE]]:23: error: expected 5-bit unsigned immediate
|
||||
dinsm $2, $3, 31, 0 # CHECK: :[[@LINE]]:27: error: expected immediate in range 2 .. 64
|
||||
dinsm $2, $3, 31, 65 # CHECK: :[[@LINE]]:27: error: expected immediate in range 2 .. 64
|
||||
dinsu $2, $3, 31, 1 # CHECK: :[[@LINE]]:23: error: expected immediate in range 32 .. 63
|
||||
dinsu $2, $3, 64, 1 # CHECK: :[[@LINE]]:23: error: expected immediate in range 32 .. 63
|
||||
dinsu $2, $3, 63, 0 # CHECK: :[[@LINE]]:27: error: expected immediate in range 1 .. 32
|
||||
dinsu $2, $3, 32, 33 # CHECK: :[[@LINE]]:27: error: expected immediate in range 1 .. 32
|
||||
|
|
Loading…
Reference in New Issue