mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-10-21 03:53:04 +02:00
[Hexagon] Adding compare byte/halfword reg-reg/reg-imm forms. Adding compare to general register reg-imm form.
llvm-svn: 224991
This commit is contained in:
parent
300c89d245
commit
c9924ffc90
@ -128,63 +128,129 @@ def C4_cmplte : T_ALU32_3op_cmp<"!cmp.gt", 0b10, 1, 0>;
|
|||||||
def C4_cmplteu : T_ALU32_3op_cmp<"!cmp.gtu", 0b11, 1, 0>;
|
def C4_cmplteu : T_ALU32_3op_cmp<"!cmp.gtu", 0b11, 1, 0>;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Generate frame index addresses.
|
// Pats for instruction selection.
|
||||||
let hasSideEffects = 0, isReMaterializable = 1,
|
|
||||||
isExtended = 1, opExtendable = 2, validSubTargets = HasV4SubT in
|
|
||||||
def TFR_FI_immext_V4 : ALU32_ri<(outs IntRegs:$dst),
|
|
||||||
(ins IntRegs:$src1, s32Imm:$offset),
|
|
||||||
"$dst = add($src1, ##$offset)",
|
|
||||||
[]>,
|
|
||||||
Requires<[HasV4T]>;
|
|
||||||
|
|
||||||
// Rd=cmp.eq(Rs,#s8)
|
// A class to embed the usual comparison patfrags within a zext to i32.
|
||||||
let validSubTargets = HasV4SubT, isExtendable = 1, opExtendable = 2,
|
// The seteq/setne frags use "lhs" and "rhs" as operands, so use the same
|
||||||
isExtentSigned = 1, opExtentBits = 8 in
|
// names, or else the frag's "body" won't match the operands.
|
||||||
def V4_A4_rcmpeqi : ALU32_ri<(outs IntRegs:$Rd),
|
class CmpInReg<PatFrag Op>
|
||||||
(ins IntRegs:$Rs, s8Ext:$s8),
|
: PatFrag<(ops node:$lhs, node:$rhs),(i32 (zext (i1 Op.Fragment)))>;
|
||||||
"$Rd = cmp.eq($Rs, #$s8)",
|
|
||||||
[(set (i32 IntRegs:$Rd),
|
|
||||||
(i32 (zext (i1 (seteq (i32 IntRegs:$Rs),
|
|
||||||
s8ExtPred:$s8)))))]>,
|
|
||||||
Requires<[HasV4T]>;
|
|
||||||
|
|
||||||
// Preserve the TSTBIT generation
|
def: T_cmp32_rr_pat<A4_rcmpeq, CmpInReg<seteq>, i32>;
|
||||||
|
def: T_cmp32_rr_pat<A4_rcmpneq, CmpInReg<setne>, i32>;
|
||||||
|
|
||||||
|
class T_CMP_rrbh<string mnemonic, bits<3> MinOp, bit IsComm>
|
||||||
|
: SInst<(outs PredRegs:$Pd), (ins IntRegs:$Rs, IntRegs:$Rt),
|
||||||
|
"$Pd = "#mnemonic#"($Rs, $Rt)", [], "", S_3op_tc_2early_SLOT23>,
|
||||||
|
ImmRegRel {
|
||||||
|
let validSubTargets = HasV4SubT;
|
||||||
|
let InputType = "reg";
|
||||||
|
let CextOpcode = mnemonic;
|
||||||
|
let isCompare = 1;
|
||||||
|
let isCommutable = IsComm;
|
||||||
|
let hasSideEffects = 0;
|
||||||
|
|
||||||
|
bits<2> Pd;
|
||||||
|
bits<5> Rs;
|
||||||
|
bits<5> Rt;
|
||||||
|
|
||||||
|
let IClass = 0b1100;
|
||||||
|
let Inst{27-21} = 0b0111110;
|
||||||
|
let Inst{20-16} = Rs;
|
||||||
|
let Inst{12-8} = Rt;
|
||||||
|
let Inst{7-5} = MinOp;
|
||||||
|
let Inst{1-0} = Pd;
|
||||||
|
}
|
||||||
|
|
||||||
|
let isCodeGenOnly = 0 in {
|
||||||
|
def A4_cmpbeq : T_CMP_rrbh<"cmpb.eq", 0b110, 1>;
|
||||||
|
def A4_cmpbgt : T_CMP_rrbh<"cmpb.gt", 0b010, 0>;
|
||||||
|
def A4_cmpbgtu : T_CMP_rrbh<"cmpb.gtu", 0b111, 0>;
|
||||||
|
def A4_cmpheq : T_CMP_rrbh<"cmph.eq", 0b011, 1>;
|
||||||
|
def A4_cmphgt : T_CMP_rrbh<"cmph.gt", 0b100, 0>;
|
||||||
|
def A4_cmphgtu : T_CMP_rrbh<"cmph.gtu", 0b101, 0>;
|
||||||
|
}
|
||||||
|
|
||||||
|
class T_CMP_ribh<string mnemonic, bits<2> MajOp, bit IsHalf, bit IsComm,
|
||||||
|
Operand ImmType, bit IsImmExt, bit IsImmSigned, int ImmBits>
|
||||||
|
: ALU64Inst<(outs PredRegs:$Pd), (ins IntRegs:$Rs, ImmType:$Imm),
|
||||||
|
"$Pd = "#mnemonic#"($Rs, #$Imm)", [], "", ALU64_tc_2early_SLOT23>,
|
||||||
|
ImmRegRel {
|
||||||
|
let validSubTargets = HasV4SubT;
|
||||||
|
let InputType = "imm";
|
||||||
|
let CextOpcode = mnemonic;
|
||||||
|
let isCompare = 1;
|
||||||
|
let isCommutable = IsComm;
|
||||||
|
let hasSideEffects = 0;
|
||||||
|
let isExtendable = IsImmExt;
|
||||||
|
let opExtendable = !if (IsImmExt, 2, 0);
|
||||||
|
let isExtentSigned = IsImmSigned;
|
||||||
|
let opExtentBits = ImmBits;
|
||||||
|
|
||||||
|
bits<2> Pd;
|
||||||
|
bits<5> Rs;
|
||||||
|
bits<8> Imm;
|
||||||
|
|
||||||
|
let IClass = 0b1101;
|
||||||
|
let Inst{27-24} = 0b1101;
|
||||||
|
let Inst{22-21} = MajOp;
|
||||||
|
let Inst{20-16} = Rs;
|
||||||
|
let Inst{12-5} = Imm;
|
||||||
|
let Inst{4} = 0b0;
|
||||||
|
let Inst{3} = IsHalf;
|
||||||
|
let Inst{1-0} = Pd;
|
||||||
|
}
|
||||||
|
|
||||||
|
let isCodeGenOnly = 0 in {
|
||||||
|
def A4_cmpbeqi : T_CMP_ribh<"cmpb.eq", 0b00, 0, 1, u8Imm, 0, 0, 8>;
|
||||||
|
def A4_cmpbgti : T_CMP_ribh<"cmpb.gt", 0b01, 0, 0, s8Imm, 0, 1, 8>;
|
||||||
|
def A4_cmpbgtui : T_CMP_ribh<"cmpb.gtu", 0b10, 0, 0, u7Ext, 1, 0, 7>;
|
||||||
|
def A4_cmpheqi : T_CMP_ribh<"cmph.eq", 0b00, 1, 1, s8Ext, 1, 1, 8>;
|
||||||
|
def A4_cmphgti : T_CMP_ribh<"cmph.gt", 0b01, 1, 0, s8Ext, 1, 1, 8>;
|
||||||
|
def A4_cmphgtui : T_CMP_ribh<"cmph.gtu", 0b10, 1, 0, u7Ext, 1, 0, 7>;
|
||||||
|
}
|
||||||
|
class T_RCMP_EQ_ri<string mnemonic, bit IsNeg>
|
||||||
|
: ALU32_ri<(outs IntRegs:$Rd), (ins IntRegs:$Rs, s8Ext:$s8),
|
||||||
|
"$Rd = "#mnemonic#"($Rs, #$s8)", [], "", ALU32_2op_tc_1_SLOT0123>,
|
||||||
|
ImmRegRel {
|
||||||
|
let validSubTargets = HasV4SubT;
|
||||||
|
let InputType = "imm";
|
||||||
|
let CextOpcode = !if (IsNeg, "!rcmp.eq", "rcmp.eq");
|
||||||
|
let isExtendable = 1;
|
||||||
|
let opExtendable = 2;
|
||||||
|
let isExtentSigned = 1;
|
||||||
|
let opExtentBits = 8;
|
||||||
|
let hasNewValue = 1;
|
||||||
|
|
||||||
|
bits<5> Rd;
|
||||||
|
bits<5> Rs;
|
||||||
|
bits<8> s8;
|
||||||
|
|
||||||
|
let IClass = 0b0111;
|
||||||
|
let Inst{27-24} = 0b0011;
|
||||||
|
let Inst{22} = 0b1;
|
||||||
|
let Inst{21} = IsNeg;
|
||||||
|
let Inst{20-16} = Rs;
|
||||||
|
let Inst{13} = 0b1;
|
||||||
|
let Inst{12-5} = s8;
|
||||||
|
let Inst{4-0} = Rd;
|
||||||
|
}
|
||||||
|
|
||||||
|
let isCodeGenOnly = 0 in {
|
||||||
|
def A4_rcmpeqi : T_RCMP_EQ_ri<"cmp.eq", 0>;
|
||||||
|
def A4_rcmpneqi : T_RCMP_EQ_ri<"!cmp.eq", 1>;
|
||||||
|
}
|
||||||
|
|
||||||
|
def: Pat<(i32 (zext (i1 (seteq (i32 IntRegs:$Rs), s8ExtPred:$s8)))),
|
||||||
|
(A4_rcmpeqi IntRegs:$Rs, s8ExtPred:$s8)>;
|
||||||
|
def: Pat<(i32 (zext (i1 (setne (i32 IntRegs:$Rs), s8ExtPred:$s8)))),
|
||||||
|
(A4_rcmpneqi IntRegs:$Rs, s8ExtPred:$s8)>;
|
||||||
|
|
||||||
|
// Preserve the S2_tstbit_r generation
|
||||||
def: Pat<(i32 (zext (i1 (setne (i32 (and (i32 (shl 1, (i32 IntRegs:$src2))),
|
def: Pat<(i32 (zext (i1 (setne (i32 (and (i32 (shl 1, (i32 IntRegs:$src2))),
|
||||||
(i32 IntRegs:$src1))), 0)))),
|
(i32 IntRegs:$src1))), 0)))),
|
||||||
(i32 (C2_muxii (i1 (S2_tstbit_r (i32 IntRegs:$src1), (i32 IntRegs:$src2))),
|
(C2_muxii (S2_tstbit_r IntRegs:$src1, IntRegs:$src2), 1, 0)>;
|
||||||
1, 0))>;
|
|
||||||
|
|
||||||
// Interfered with tstbit generation, above pattern preserves, see : tstbit.ll
|
|
||||||
// Rd=cmp.ne(Rs,#s8)
|
|
||||||
let validSubTargets = HasV4SubT, isExtendable = 1, opExtendable = 2,
|
|
||||||
isExtentSigned = 1, opExtentBits = 8 in
|
|
||||||
def V4_A4_rcmpneqi : ALU32_ri<(outs IntRegs:$Rd),
|
|
||||||
(ins IntRegs:$Rs, s8Ext:$s8),
|
|
||||||
"$Rd = !cmp.eq($Rs, #$s8)",
|
|
||||||
[(set (i32 IntRegs:$Rd),
|
|
||||||
(i32 (zext (i1 (setne (i32 IntRegs:$Rs),
|
|
||||||
s8ExtPred:$s8)))))]>,
|
|
||||||
Requires<[HasV4T]>;
|
|
||||||
|
|
||||||
// Rd=cmp.eq(Rs,Rt)
|
|
||||||
let validSubTargets = HasV4SubT in
|
|
||||||
def V4_A4_rcmpeq : ALU32_ri<(outs IntRegs:$Rd),
|
|
||||||
(ins IntRegs:$Rs, IntRegs:$Rt),
|
|
||||||
"$Rd = cmp.eq($Rs, $Rt)",
|
|
||||||
[(set (i32 IntRegs:$Rd),
|
|
||||||
(i32 (zext (i1 (seteq (i32 IntRegs:$Rs),
|
|
||||||
IntRegs:$Rt)))))]>,
|
|
||||||
Requires<[HasV4T]>;
|
|
||||||
|
|
||||||
// Rd=cmp.ne(Rs,Rt)
|
|
||||||
let validSubTargets = HasV4SubT in
|
|
||||||
def V4_A4_rcmpneq : ALU32_ri<(outs IntRegs:$Rd),
|
|
||||||
(ins IntRegs:$Rs, IntRegs:$Rt),
|
|
||||||
"$Rd = !cmp.eq($Rs, $Rt)",
|
|
||||||
[(set (i32 IntRegs:$Rd),
|
|
||||||
(i32 (zext (i1 (setne (i32 IntRegs:$Rs),
|
|
||||||
IntRegs:$Rt)))))]>,
|
|
||||||
Requires<[HasV4T]>;
|
|
||||||
|
|
||||||
//===----------------------------------------------------------------------===//
|
//===----------------------------------------------------------------------===//
|
||||||
// ALU32 -
|
// ALU32 -
|
||||||
|
@ -60,6 +60,10 @@
|
|||||||
# CHECK: p3 = cmp.gtu(r21, r31)
|
# CHECK: p3 = cmp.gtu(r21, r31)
|
||||||
0x13 0xdf 0x75 0xf2
|
0x13 0xdf 0x75 0xf2
|
||||||
# CHECK: p3 = !cmp.gtu(r21, r31)
|
# CHECK: p3 = !cmp.gtu(r21, r31)
|
||||||
|
0xf1 0xe3 0x55 0x73
|
||||||
|
# CHECK: r17 = cmp.eq(r21, #31)
|
||||||
|
0xf1 0xe3 0x75 0x73
|
||||||
|
# CHECK: r17 = !cmp.eq(r21, #31)
|
||||||
0x11 0xdf 0x55 0xf3
|
0x11 0xdf 0x55 0xf3
|
||||||
# CHECK: r17 = cmp.eq(r21, r31)
|
# CHECK: r17 = cmp.eq(r21, r31)
|
||||||
0x11 0xdf 0x75 0xf3
|
0x11 0xdf 0x75 0xf3
|
||||||
|
@ -1,5 +1,29 @@
|
|||||||
# RUN: llvm-mc --triple hexagon -disassemble < %s | FileCheck %s
|
# RUN: llvm-mc --triple hexagon -disassemble < %s | FileCheck %s
|
||||||
|
|
||||||
|
0x43 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmpb.gt(r17, r21)
|
||||||
|
0xc3 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmpb.eq(r17, r21)
|
||||||
|
0xe3 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmpb.gtu(r17, r21)
|
||||||
|
0xa3 0xc2 0x11 0xdd
|
||||||
|
# CHECK: p3 = cmpb.eq(r17, #21)
|
||||||
|
0xa3 0xc2 0x31 0xdd
|
||||||
|
# CHECK: p3 = cmpb.gt(r17, #21)
|
||||||
|
0xa3 0xc2 0x51 0xdd
|
||||||
|
# CHECK: p3 = cmpb.gtu(r17, #21)
|
||||||
|
0x63 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmph.eq(r17, r21)
|
||||||
|
0x83 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmph.gt(r17, r21)
|
||||||
|
0xa3 0xd5 0xd1 0xc7
|
||||||
|
# CHECK: p3 = cmph.gtu(r17, r21)
|
||||||
|
0xab 0xc2 0x11 0xdd
|
||||||
|
# CHECK: p3 = cmph.eq(r17, #21)
|
||||||
|
0xab 0xc2 0x31 0xdd
|
||||||
|
# CHECK: p3 = cmph.gt(r17, #21)
|
||||||
|
0xab 0xc2 0x51 0xdd
|
||||||
|
# CHECK: p3 = cmph.gtu(r17, #21)
|
||||||
0x03 0xde 0x94 0xd2
|
0x03 0xde 0x94 0xd2
|
||||||
# CHECK: p3 = cmp.eq(r21:20, r31:30)
|
# CHECK: p3 = cmp.eq(r21:20, r31:30)
|
||||||
0x43 0xde 0x94 0xd2
|
0x43 0xde 0x94 0xd2
|
||||||
|
Loading…
Reference in New Issue
Block a user