summaryrefslogtreecommitdiff
path: root/lib/Target/Hexagon/HexagonInstrInfoV4.td
diff options
context:
space:
mode:
authorJyotsna Verma <jverma@codeaurora.org>2013-05-02 21:21:57 +0000
committerJyotsna Verma <jverma@codeaurora.org>2013-05-02 21:21:57 +0000
commit8a3f50038fa68e1c6697152ee08ad0f2faacb0b7 (patch)
treedb6fb2c474c587d37c55e0ea95cba6b7c7bc3867 /lib/Target/Hexagon/HexagonInstrInfoV4.td
parent556dd3a9a9068337a84e3ba32253a10cd1ab67dc (diff)
downloadllvm-8a3f50038fa68e1c6697152ee08ad0f2faacb0b7.tar.gz
llvm-8a3f50038fa68e1c6697152ee08ad0f2faacb0b7.tar.bz2
llvm-8a3f50038fa68e1c6697152ee08ad0f2faacb0b7.tar.xz
Hexagon: Add multiclass/encoding bits for the New-Value Jump instructions.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@180953 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/Hexagon/HexagonInstrInfoV4.td')
-rw-r--r--lib/Target/Hexagon/HexagonInstrInfoV4.td313
1 files changed, 164 insertions, 149 deletions
diff --git a/lib/Target/Hexagon/HexagonInstrInfoV4.td b/lib/Target/Hexagon/HexagonInstrInfoV4.td
index 744efe85ec..933239d5c3 100644
--- a/lib/Target/Hexagon/HexagonInstrInfoV4.td
+++ b/lib/Target/Hexagon/HexagonInstrInfoV4.td
@@ -967,179 +967,193 @@ defm POST_STwri: ST_PostInc_nv <"memw", "STriw", IntRegs, s4_2Imm>, AddrModeRel;
// NV/J +
//===----------------------------------------------------------------------===//
-multiclass NVJ_type_basic_reg<string NotStr, string OpcStr, string TakenStr> {
- def _ie_nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, IntRegs:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, $src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
-
- def _nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, IntRegs:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, $src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+//===----------------------------------------------------------------------===//
+// multiclass/template class for the new-value compare jumps with the register
+// operands.
+//===----------------------------------------------------------------------===//
+
+let isExtendable = 1, opExtendable = 2, isExtentSigned = 1, opExtentBits = 11 in
+class NVJrr_template<string mnemonic, bits<3> majOp, bit NvOpNum,
+ bit isNegCond, bit isTaken>
+ : NVInst_V4<(outs),
+ (ins IntRegs:$src1, IntRegs:$src2, brtarget:$offset),
+ "if ("#!if(isNegCond, "!","")#mnemonic#
+ "($src1"#!if(!eq(NvOpNum, 0),".new, ",", ")#
+ "$src2"#!if(!eq(NvOpNum, 1),".new))","))")#" jump:"
+ #!if(isTaken, "t","nt")#" $offset",
+ []>, Requires<[HasV4T]> {
+
+ bits<5> src1;
+ bits<5> src2;
+ bits<3> Ns; // New-Value Operand
+ bits<5> RegOp; // Non New-Value Operand
+ bits<11> offset;
+
+ let isBrTaken = !if(isTaken, "true", "false");
+ let isPredicatedFalse = isNegCond;
+
+ let Ns = !if(!eq(NvOpNum, 0), src1{2-0}, src2{2-0});
+ let RegOp = !if(!eq(NvOpNum, 0), src2, src1);
+
+ let IClass = 0b0010;
+ let Inst{26} = 0b0;
+ let Inst{25-23} = majOp;
+ let Inst{22} = isNegCond;
+ let Inst{18-16} = Ns;
+ let Inst{13} = isTaken;
+ let Inst{12-8} = RegOp;
+ let Inst{21-20} = offset{10-9};
+ let Inst{7-1} = offset{8-2};
+}
+
+
+multiclass NVJrr_cond<string mnemonic, bits<3> majOp, bit NvOpNum,
+ bit isNegCond> {
+ // Branch not taken:
+ def _nt_V4: NVJrr_template<mnemonic, majOp, NvOpNum, isNegCond, 0>;
+ // Branch taken:
+ def _t_V4: NVJrr_template<mnemonic, majOp, NvOpNum, isNegCond, 1>;
+}
+
+// NvOpNum = 0 -> First Operand is a new-value Register
+// NvOpNum = 1 -> Second Operand is a new-value Register
+
+multiclass NVJrr_base<string mnemonic, string BaseOp, bits<3> majOp,
+ bit NvOpNum> {
+ let BaseOpcode = BaseOp#_NVJ in {
+ defm _t_Jumpnv : NVJrr_cond<mnemonic, majOp, NvOpNum, 0>; // True cond
+ defm _f_Jumpnv : NVJrr_cond<mnemonic, majOp, NvOpNum, 1>; // False cond
+ }
}
-multiclass NVJ_type_basic_2ndDotNew<string NotStr, string OpcStr,
- string TakenStr> {
- def _ie_nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, IntRegs:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1, $src2.new)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+// if ([!]cmp.eq(Ns.new,Rt)) jump:[n]t #r9:2
+// if ([!]cmp.gt(Ns.new,Rt)) jump:[n]t #r9:2
+// if ([!]cmp.gtu(Ns.new,Rt)) jump:[n]t #r9:2
+// if ([!]cmp.gt(Rt,Ns.new)) jump:[n]t #r9:2
+// if ([!]cmp.gtu(Rt,Ns.new)) jump:[n]t #r9:2
- def _nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, IntRegs:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1, $src2.new)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+let isPredicated = 1, isBranch = 1, isNewValue = 1, isTerminator = 1,
+ Defs = [PC], neverHasSideEffects = 1, validSubTargets = HasV4SubT in {
+ defm CMPEQrr : NVJrr_base<"cmp.eq", "CMPEQ", 0b000, 0>, PredRel;
+ defm CMPGTrr : NVJrr_base<"cmp.gt", "CMPGT", 0b001, 0>, PredRel;
+ defm CMPGTUrr : NVJrr_base<"cmp.gtu", "CMPGTU", 0b010, 0>, PredRel;
+ defm CMPLTrr : NVJrr_base<"cmp.gt", "CMPLT", 0b011, 1>, PredRel;
+ defm CMPLTUrr : NVJrr_base<"cmp.gtu", "CMPLTU", 0b100, 1>, PredRel;
}
-multiclass NVJ_type_basic_imm<string NotStr, string OpcStr, string TakenStr> {
- def _ie_nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, u5Imm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+//===----------------------------------------------------------------------===//
+// multiclass/template class for the new-value compare jumps instruction
+// with a register and an unsigned immediate (U5) operand.
+//===----------------------------------------------------------------------===//
- def _nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, u5Imm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
-}
+let isExtendable = 1, opExtendable = 2, isExtentSigned = 1, opExtentBits = 11 in
+class NVJri_template<string mnemonic, bits<3> majOp, bit isNegCond,
+ bit isTaken>
+ : NVInst_V4<(outs),
+ (ins IntRegs:$src1, u5Imm:$src2, brtarget:$offset),
+ "if ("#!if(isNegCond, "!","")#mnemonic#"($src1.new, #$src2)) jump:"
+ #!if(isTaken, "t","nt")#" $offset",
+ []>, Requires<[HasV4T]> {
-multiclass NVJ_type_basic_neg<string NotStr, string OpcStr, string TakenStr> {
- def _ie_nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, nOneImm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+ let isPredicatedFalse = isNegCond;
+ let isBrTaken = !if(isTaken, "true", "false");
- def _nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, nOneImm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
-}
-
-multiclass NVJ_type_basic_tstbit<string NotStr, string OpcStr,
- string TakenStr> {
- def _ie_nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, u1Imm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+ bits<3> src1;
+ bits<5> src2;
+ bits<11> offset;
- def _nv_V4 : NVInst_V4<(outs),
- (ins IntRegs:$src1, u1Imm:$src2, brtarget:$offset),
- !strconcat("if (", !strconcat(NotStr, !strconcat(OpcStr,
- !strconcat("($src1.new, #$src2)) jump:",
- !strconcat(TakenStr, " $offset"))))),
- []>,
- Requires<[HasV4T]>;
+ let IClass = 0b0010;
+ let Inst{26} = 0b1;
+ let Inst{25-23} = majOp;
+ let Inst{22} = isNegCond;
+ let Inst{18-16} = src1;
+ let Inst{13} = isTaken;
+ let Inst{12-8} = src2;
+ let Inst{21-20} = offset{10-9};
+ let Inst{7-1} = offset{8-2};
}
-// Multiclass for regular dot new of Ist operand register.
-multiclass NVJ_type_br_pred_reg<string NotStr, string OpcStr> {
- defm Pt : NVJ_type_basic_reg<NotStr, OpcStr, "t">;
- defm Pnt : NVJ_type_basic_reg<NotStr, OpcStr, "nt">;
+multiclass NVJri_cond<string mnemonic, bits<3> majOp, bit isNegCond> {
+ // Branch not taken:
+ def _nt_V4: NVJri_template<mnemonic, majOp, isNegCond, 0>;
+ // Branch taken:
+ def _t_V4: NVJri_template<mnemonic, majOp, isNegCond, 1>;
}
-// Multiclass for dot new of 2nd operand register.
-multiclass NVJ_type_br_pred_2ndDotNew<string NotStr, string OpcStr> {
- defm Pt : NVJ_type_basic_2ndDotNew<NotStr, OpcStr, "t">;
- defm Pnt : NVJ_type_basic_2ndDotNew<NotStr, OpcStr, "nt">;
+multiclass NVJri_base<string mnemonic, string BaseOp, bits<3> majOp> {
+ let BaseOpcode = BaseOp#_NVJri in {
+ defm _t_Jumpnv : NVJri_cond<mnemonic, majOp, 0>; // True Cond
+ defm _f_Jumpnv : NVJri_cond<mnemonic, majOp, 1>; // False cond
+ }
}
-// Multiclass for 2nd operand immediate, including -1.
-multiclass NVJ_type_br_pred_imm<string NotStr, string OpcStr> {
- defm Pt : NVJ_type_basic_imm<NotStr, OpcStr, "t">;
- defm Pnt : NVJ_type_basic_imm<NotStr, OpcStr, "nt">;
- defm Ptneg : NVJ_type_basic_neg<NotStr, OpcStr, "t">;
- defm Pntneg : NVJ_type_basic_neg<NotStr, OpcStr, "nt">;
-}
+// if ([!]cmp.eq(Ns.new,#U5)) jump:[n]t #r9:2
+// if ([!]cmp.gt(Ns.new,#U5)) jump:[n]t #r9:2
+// if ([!]cmp.gtu(Ns.new,#U5)) jump:[n]t #r9:2
-// Multiclass for 2nd operand immediate, excluding -1.
-multiclass NVJ_type_br_pred_imm_only<string NotStr, string OpcStr> {
- defm Pt : NVJ_type_basic_imm<NotStr, OpcStr, "t">;
- defm Pnt : NVJ_type_basic_imm<NotStr, OpcStr, "nt">;
+let isPredicated = 1, isBranch = 1, isNewValue = 1, isTerminator = 1,
+ Defs = [PC], neverHasSideEffects = 1, validSubTargets = HasV4SubT in {
+ defm CMPEQri : NVJri_base<"cmp.eq", "CMPEQ", 0b000>, PredRel;
+ defm CMPGTri : NVJri_base<"cmp.gt", "CMPGT", 0b001>, PredRel;
+ defm CMPGTUri : NVJri_base<"cmp.gtu", "CMPGTU", 0b010>, PredRel;
}
-// Multiclass for tstbit, where 2nd operand is always #0.
-multiclass NVJ_type_br_pred_tstbit<string NotStr, string OpcStr> {
- defm Pt : NVJ_type_basic_tstbit<NotStr, OpcStr, "t">;
- defm Pnt : NVJ_type_basic_tstbit<NotStr, OpcStr, "nt">;
-}
+//===----------------------------------------------------------------------===//
+// multiclass/template class for the new-value compare jumps instruction
+// with a register and an hardcoded 0/-1 immediate value.
+//===----------------------------------------------------------------------===//
-// Multiclass for GT.
-multiclass NVJ_type_rr_ri<string OpcStr> {
- defm rrNot : NVJ_type_br_pred_reg<"!", OpcStr>;
- defm rr : NVJ_type_br_pred_reg<"", OpcStr>;
- defm rrdnNot : NVJ_type_br_pred_2ndDotNew<"!", OpcStr>;
- defm rrdn : NVJ_type_br_pred_2ndDotNew<"", OpcStr>;
- defm riNot : NVJ_type_br_pred_imm<"!", OpcStr>;
- defm ri : NVJ_type_br_pred_imm<"", OpcStr>;
-}
+let isExtendable = 1, opExtendable = 1, isExtentSigned = 1, opExtentBits = 11 in
+class NVJ_ConstImm_template<string mnemonic, bits<3> majOp, string ImmVal,
+ bit isNegCond, bit isTaken>
+ : NVInst_V4<(outs),
+ (ins IntRegs:$src1, brtarget:$offset),
+ "if ("#!if(isNegCond, "!","")#mnemonic
+ #"($src1.new, #"#ImmVal#")) jump:"
+ #!if(isTaken, "t","nt")#" $offset",
+ []>, Requires<[HasV4T]> {
-// Multiclass for EQ.
-multiclass NVJ_type_rr_ri_no_2ndDotNew<string OpcStr> {
- defm rrNot : NVJ_type_br_pred_reg<"!", OpcStr>;
- defm rr : NVJ_type_br_pred_reg<"", OpcStr>;
- defm riNot : NVJ_type_br_pred_imm<"!", OpcStr>;
- defm ri : NVJ_type_br_pred_imm<"", OpcStr>;
-}
+ let isPredicatedFalse = isNegCond;
+ let isBrTaken = !if(isTaken, "true", "false");
-// Multiclass for GTU.
-multiclass NVJ_type_rr_ri_no_nOne<string OpcStr> {
- defm rrNot : NVJ_type_br_pred_reg<"!", OpcStr>;
- defm rr : NVJ_type_br_pred_reg<"", OpcStr>;
- defm rrdnNot : NVJ_type_br_pred_2ndDotNew<"!", OpcStr>;
- defm rrdn : NVJ_type_br_pred_2ndDotNew<"", OpcStr>;
- defm riNot : NVJ_type_br_pred_imm_only<"!", OpcStr>;
- defm ri : NVJ_type_br_pred_imm_only<"", OpcStr>;
+ bits<3> src1;
+ bits<11> offset;
+ let IClass = 0b0010;
+ let Inst{26} = 0b1;
+ let Inst{25-23} = majOp;
+ let Inst{22} = isNegCond;
+ let Inst{18-16} = src1;
+ let Inst{13} = isTaken;
+ let Inst{21-20} = offset{10-9};
+ let Inst{7-1} = offset{8-2};
}
-// Multiclass for tstbit.
-multiclass NVJ_type_r0<string OpcStr> {
- defm r0Not : NVJ_type_br_pred_tstbit<"!", OpcStr>;
- defm r0 : NVJ_type_br_pred_tstbit<"", OpcStr>;
- }
-
-// Base Multiclass for New Value Jump.
-multiclass NVJ_type {
- defm GT : NVJ_type_rr_ri<"cmp.gt">;
- defm EQ : NVJ_type_rr_ri_no_2ndDotNew<"cmp.eq">;
- defm GTU : NVJ_type_rr_ri_no_nOne<"cmp.gtu">;
- defm TSTBIT : NVJ_type_r0<"tstbit">;
+multiclass NVJ_ConstImm_cond<string mnemonic, bits<3> majOp, string ImmVal,
+ bit isNegCond> {
+ // Branch not taken:
+ def _nt_V4: NVJ_ConstImm_template<mnemonic, majOp, ImmVal, isNegCond, 0>;
+ // Branch taken:
+ def _t_V4: NVJ_ConstImm_template<mnemonic, majOp, ImmVal, isNegCond, 1>;
}
-let isBranch = 1, isTerminator=1, neverHasSideEffects = 1, Defs = [PC] in {
- defm JMP_ : NVJ_type;
+multiclass NVJ_ConstImm_base<string mnemonic, string BaseOp, bits<3> majOp,
+ string ImmVal> {
+ let BaseOpcode = BaseOp#_NVJ_ConstImm in {
+ defm _t_Jumpnv : NVJ_ConstImm_cond<mnemonic, majOp, ImmVal, 0>; // True cond
+ defm _f_Jumpnv : NVJ_ConstImm_cond<mnemonic, majOp, ImmVal, 1>; // False Cond
+ }
}
-//===----------------------------------------------------------------------===//
-// NV/J -
-//===----------------------------------------------------------------------===//
+// if ([!]tstbit(Ns.new,#0)) jump:[n]t #r9:2
+// if ([!]cmp.eq(Ns.new,#-1)) jump:[n]t #r9:2
+// if ([!]cmp.gt(Ns.new,#-1)) jump:[n]t #r9:2
+
+let isPredicated = 1, isBranch = 1, isNewValue = 1, isTerminator=1,
+ Defs = [PC], neverHasSideEffects = 1 in {
+ defm TSTBIT0 : NVJ_ConstImm_base<"tstbit", "TSTBIT", 0b011, "0">, PredRel;
+ defm CMPEQn1 : NVJ_ConstImm_base<"cmp.eq", "CMPEQ", 0b100, "-1">, PredRel;
+ defm CMPGTn1 : NVJ_ConstImm_base<"cmp.gt", "CMPGT", 0b101, "-1">, PredRel;
+}
//===----------------------------------------------------------------------===//
// XTYPE/ALU +
@@ -3007,9 +3021,10 @@ def : Pat <(i32 (load (HexagonCONST32_GP tglobaladdr:$global))),
// Transfer global address into a register
-let AddedComplexity=50, isMoveImm = 1, isReMaterializable = 1 in
-def TFRI_V4 : ALU32_ri<(outs IntRegs:$dst), (ins globaladdress:$src1),
- "$dst = ##$src1",
+let isExtended = 1, opExtendable = 1, AddedComplexity=50, isMoveImm = 1,
+isAsCheapAsAMove = 1, isReMaterializable = 1, validSubTargets = HasV4SubT in
+def TFRI_V4 : ALU32_ri<(outs IntRegs:$dst), (ins s16Ext:$src1),
+ "$dst = #$src1",
[(set IntRegs:$dst, (HexagonCONST32 tglobaladdr:$src1))]>,
Requires<[HasV4T]>;