mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-02-19 06:31:18 +00:00
Range checking for CDP[2] immediates.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@135092 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
466b022c99
commit
83ab070fc1
@ -459,6 +459,22 @@ def arm_i32imm : PatLeaf<(imm), [{
|
|||||||
return ARM_AM::isSOImmTwoPartVal((unsigned)N->getZExtValue());
|
return ARM_AM::isSOImmTwoPartVal((unsigned)N->getZExtValue());
|
||||||
}]>;
|
}]>;
|
||||||
|
|
||||||
|
/// imm0_7 predicate - Immediate in the range [0,31].
|
||||||
|
def Imm0_7AsmOperand: AsmOperandClass { let Name = "Imm0_7"; }
|
||||||
|
def imm0_7 : Operand<i32>, ImmLeaf<i32, [{
|
||||||
|
return Imm >= 0 && Imm < 8;
|
||||||
|
}]> {
|
||||||
|
let ParserMatchClass = Imm0_7AsmOperand;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// imm0_15 predicate - Immediate in the range [0,31].
|
||||||
|
def Imm0_15AsmOperand: AsmOperandClass { let Name = "Imm0_15"; }
|
||||||
|
def imm0_15 : Operand<i32>, ImmLeaf<i32, [{
|
||||||
|
return Imm >= 0 && Imm < 16;
|
||||||
|
}]> {
|
||||||
|
let ParserMatchClass = Imm0_15AsmOperand;
|
||||||
|
}
|
||||||
|
|
||||||
/// imm0_31 predicate - True if the 32-bit immediate is in the range [0,31].
|
/// imm0_31 predicate - True if the 32-bit immediate is in the range [0,31].
|
||||||
def imm0_31 : Operand<i32>, ImmLeaf<i32, [{
|
def imm0_31 : Operand<i32>, ImmLeaf<i32, [{
|
||||||
return Imm >= 0 && Imm < 32;
|
return Imm >= 0 && Imm < 32;
|
||||||
@ -3465,8 +3481,8 @@ def SWPB : AIswp<1, (outs GPR:$Rt), (ins GPR:$Rt2, GPR:$Rn), "swpb",
|
|||||||
// Coprocessor Instructions.
|
// Coprocessor Instructions.
|
||||||
//
|
//
|
||||||
|
|
||||||
def CDP : ABI<0b1110, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
def CDP : ABI<0b1110, (outs), (ins p_imm:$cop, imm0_15:$opc1,
|
||||||
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, i32imm:$opc2),
|
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, imm0_7:$opc2),
|
||||||
NoItinerary, "cdp", "\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
NoItinerary, "cdp", "\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
||||||
[(int_arm_cdp imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
[(int_arm_cdp imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
||||||
imm:$CRm, imm:$opc2)]> {
|
imm:$CRm, imm:$opc2)]> {
|
||||||
@ -3486,8 +3502,8 @@ def CDP : ABI<0b1110, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
|||||||
let Inst{23-20} = opc1;
|
let Inst{23-20} = opc1;
|
||||||
}
|
}
|
||||||
|
|
||||||
def CDP2 : ABXI<0b1110, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
def CDP2 : ABXI<0b1110, (outs), (ins p_imm:$cop, imm0_15:$opc1,
|
||||||
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, i32imm:$opc2),
|
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, imm0_7:$opc2),
|
||||||
NoItinerary, "cdp2\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
NoItinerary, "cdp2\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
||||||
[(int_arm_cdp2 imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
[(int_arm_cdp2 imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
||||||
imm:$CRm, imm:$opc2)]> {
|
imm:$CRm, imm:$opc2)]> {
|
||||||
|
@ -26,10 +26,6 @@ def imm_comp_XFORM : SDNodeXForm<imm, [{
|
|||||||
return CurDAG->getTargetConstant(~((uint32_t)N->getZExtValue()), MVT::i32);
|
return CurDAG->getTargetConstant(~((uint32_t)N->getZExtValue()), MVT::i32);
|
||||||
}]>;
|
}]>;
|
||||||
|
|
||||||
/// imm0_7 predicate - True if the 32-bit immediate is in the range [0,7].
|
|
||||||
def imm0_7 : ImmLeaf<i32, [{
|
|
||||||
return Imm >= 0 && Imm < 8;
|
|
||||||
}]>;
|
|
||||||
def imm0_7_neg : PatLeaf<(i32 imm), [{
|
def imm0_7_neg : PatLeaf<(i32 imm), [{
|
||||||
return (uint32_t)-N->getZExtValue() < 8;
|
return (uint32_t)-N->getZExtValue() < 8;
|
||||||
}], imm_neg_XFORM>;
|
}], imm_neg_XFORM>;
|
||||||
|
@ -3421,8 +3421,8 @@ def t2MRRC2 : t2MovRRCopro<0b1111, "mrrc2", 1>;
|
|||||||
// Other Coprocessor Instructions.
|
// Other Coprocessor Instructions.
|
||||||
//
|
//
|
||||||
|
|
||||||
def tCDP : T2Cop<0b1110, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
def tCDP : T2Cop<0b1110, (outs), (ins p_imm:$cop, imm0_15:$opc1,
|
||||||
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, i32imm:$opc2),
|
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, imm0_7:$opc2),
|
||||||
"cdp\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
"cdp\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
||||||
[(int_arm_cdp imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
[(int_arm_cdp imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
||||||
imm:$CRm, imm:$opc2)]> {
|
imm:$CRm, imm:$opc2)]> {
|
||||||
@ -3444,8 +3444,8 @@ def tCDP : T2Cop<0b1110, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
|||||||
let Inst{23-20} = opc1;
|
let Inst{23-20} = opc1;
|
||||||
}
|
}
|
||||||
|
|
||||||
def t2CDP2 : T2Cop<0b1111, (outs), (ins p_imm:$cop, i32imm:$opc1,
|
def t2CDP2 : T2Cop<0b1111, (outs), (ins p_imm:$cop, imm0_15:$opc1,
|
||||||
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, i32imm:$opc2),
|
c_imm:$CRd, c_imm:$CRn, c_imm:$CRm, imm0_7:$opc2),
|
||||||
"cdp2\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
"cdp2\t$cop, $opc1, $CRd, $CRn, $CRm, $opc2",
|
||||||
[(int_arm_cdp2 imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
[(int_arm_cdp2 imm:$cop, imm:$opc1, imm:$CRd, imm:$CRn,
|
||||||
imm:$CRm, imm:$opc2)]> {
|
imm:$CRm, imm:$opc2)]> {
|
||||||
|
@ -386,6 +386,22 @@ public:
|
|||||||
int64_t Value = CE->getValue();
|
int64_t Value = CE->getValue();
|
||||||
return Value >= 0 && Value < 256;
|
return Value >= 0 && Value < 256;
|
||||||
}
|
}
|
||||||
|
bool isImm0_7() const {
|
||||||
|
if (Kind != Immediate)
|
||||||
|
return false;
|
||||||
|
const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
|
||||||
|
if (!CE) return false;
|
||||||
|
int64_t Value = CE->getValue();
|
||||||
|
return Value >= 0 && Value < 8;
|
||||||
|
}
|
||||||
|
bool isImm0_15() const {
|
||||||
|
if (Kind != Immediate)
|
||||||
|
return false;
|
||||||
|
const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
|
||||||
|
if (!CE) return false;
|
||||||
|
int64_t Value = CE->getValue();
|
||||||
|
return Value >= 0 && Value < 16;
|
||||||
|
}
|
||||||
bool isImm0_65535() const {
|
bool isImm0_65535() const {
|
||||||
if (Kind != Immediate)
|
if (Kind != Immediate)
|
||||||
return false;
|
return false;
|
||||||
@ -585,6 +601,16 @@ public:
|
|||||||
addExpr(Inst, getImm());
|
addExpr(Inst, getImm());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void addImm0_7Operands(MCInst &Inst, unsigned N) const {
|
||||||
|
assert(N == 1 && "Invalid number of operands!");
|
||||||
|
addExpr(Inst, getImm());
|
||||||
|
}
|
||||||
|
|
||||||
|
void addImm0_15Operands(MCInst &Inst, unsigned N) const {
|
||||||
|
assert(N == 1 && "Invalid number of operands!");
|
||||||
|
addExpr(Inst, getImm());
|
||||||
|
}
|
||||||
|
|
||||||
void addImm0_65535Operands(MCInst &Inst, unsigned N) const {
|
void addImm0_65535Operands(MCInst &Inst, unsigned N) const {
|
||||||
assert(N == 1 && "Invalid number of operands!");
|
assert(N == 1 && "Invalid number of operands!");
|
||||||
addExpr(Inst, getImm());
|
addExpr(Inst, getImm());
|
||||||
|
@ -357,3 +357,17 @@ _func:
|
|||||||
|
|
||||||
@ CHECK: bxj r2 @ encoding: [0x22,0xff,0x2f,0xe1]
|
@ CHECK: bxj r2 @ encoding: [0x22,0xff,0x2f,0xe1]
|
||||||
@ CHECK: bxjne r2 @ encoding: [0x22,0xff,0x2f,0x11]
|
@ CHECK: bxjne r2 @ encoding: [0x22,0xff,0x2f,0x11]
|
||||||
|
|
||||||
|
@------------------------------------------------------------------------------
|
||||||
|
@ FIXME: CBNZ/CBZ
|
||||||
|
@------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
@------------------------------------------------------------------------------
|
||||||
|
@ CDP/CDP2
|
||||||
|
@------------------------------------------------------------------------------
|
||||||
|
cdp p7, #1, c1, c1, c1, #4
|
||||||
|
cdp2 p7, #1, c1, c1, c1, #4
|
||||||
|
|
||||||
|
@ CHECK: cdp p7, #1, c1, c1, c1, #4 @ encoding: [0x81,0x17,0x11,0xee]
|
||||||
|
@ CHECK: cdp2 p7, #1, c1, c1, c1, #4 @ encoding: [0x81,0x17,0x11,0xfe]
|
||||||
|
@ -45,4 +45,17 @@
|
|||||||
@ Out of range 16-bit immediate on BKPT
|
@ Out of range 16-bit immediate on BKPT
|
||||||
bkpt #65536
|
bkpt #65536
|
||||||
|
|
||||||
|
@ CHECK-ERRORS: error: invalid operand for instruction
|
||||||
|
|
||||||
|
@ Out of range 4 and 3 bit immediates on CDP[2]
|
||||||
|
|
||||||
|
@ Out of range immediates for CDP/CDP2
|
||||||
|
cdp p7, #2, c1, c1, c1, #8
|
||||||
|
cdp p7, #1, c1, c1, c1, #8
|
||||||
|
cdp2 p7, #2, c1, c1, c1, #8
|
||||||
|
cdp2 p7, #1, c1, c1, c1, #8
|
||||||
|
|
||||||
|
@ CHECK-ERRORS: error: invalid operand for instruction
|
||||||
|
@ CHECK-ERRORS: error: invalid operand for instruction
|
||||||
|
@ CHECK-ERRORS: error: invalid operand for instruction
|
||||||
@ CHECK-ERRORS: error: invalid operand for instruction
|
@ CHECK-ERRORS: error: invalid operand for instruction
|
||||||
|
@ -588,6 +588,8 @@ static int ARMFlagFromOpName(LiteralConstantEmitter *type,
|
|||||||
IMM("imm0_31");
|
IMM("imm0_31");
|
||||||
IMM("imm0_31_m1");
|
IMM("imm0_31_m1");
|
||||||
IMM("nModImm");
|
IMM("nModImm");
|
||||||
|
IMM("imm0_7");
|
||||||
|
IMM("imm0_15");
|
||||||
IMM("imm0_255");
|
IMM("imm0_255");
|
||||||
IMM("imm0_4095");
|
IMM("imm0_4095");
|
||||||
IMM("imm0_65535");
|
IMM("imm0_65535");
|
||||||
|
Loading…
x
Reference in New Issue
Block a user