blob: 55c7aa2bd86591a438877e40887385ce5022b025 [file] [log] [blame]
Anton Korobeynikovf2e14752009-05-29 23:41:08 +00001//===- ARMInstrThumb2.td - Thumb2 support for ARM -------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file describes the Thumb2 instruction set.
11//
12//===----------------------------------------------------------------------===//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000013
Evan Chengd5b67fa2009-07-10 01:54:42 +000014// IT block predicate field
15def it_pred : Operand<i32> {
16 let PrintMethod = "printPredicateOperand";
17}
18
19// IT block condition mask
20def it_mask : Operand<i32> {
21 let PrintMethod = "printThumbITMask";
22}
23
Evan Cheng1b2b3e22009-07-29 02:18:14 +000024// Table branch address
25def tb_addrmode : Operand<i32> {
26 let PrintMethod = "printTBAddrMode";
27}
28
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000029// Shifted operands. No register controlled shifts for Thumb2.
30// Note: We do not support rrx shifted operands yet.
31def t2_so_reg : Operand<i32>, // reg imm
Evan Cheng19bb7c72009-06-27 02:26:13 +000032 ComplexPattern<i32, 2, "SelectT2ShifterOperandReg",
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000033 [shl,srl,sra,rotr]> {
Evan Cheng19bb7c72009-06-27 02:26:13 +000034 let PrintMethod = "printT2SOOperand";
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000035 let MIOperandInfo = (ops GPR, i32imm);
36}
37
Evan Cheng36173712009-06-23 17:48:47 +000038// t2_so_imm_not_XFORM - Return the complement of a t2_so_imm value
39def t2_so_imm_not_XFORM : SDNodeXForm<imm, [{
Owen Anderson36e3a6e2009-08-11 20:47:22 +000040 return CurDAG->getTargetConstant(~((uint32_t)N->getZExtValue()), MVT::i32);
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000041}]>;
42
Evan Cheng36173712009-06-23 17:48:47 +000043// t2_so_imm_neg_XFORM - Return the negation of a t2_so_imm value
44def t2_so_imm_neg_XFORM : SDNodeXForm<imm, [{
Owen Anderson36e3a6e2009-08-11 20:47:22 +000045 return CurDAG->getTargetConstant(-((int)N->getZExtValue()), MVT::i32);
Evan Cheng36173712009-06-23 17:48:47 +000046}]>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000047
Evan Cheng36173712009-06-23 17:48:47 +000048// t2_so_imm - Match a 32-bit immediate operand, which is an
49// 8-bit immediate rotated by an arbitrary number of bits, or an 8-bit
50// immediate splatted into multiple bytes of the word. t2_so_imm values are
51// represented in the imm field in the same 12-bit form that they are encoded
Jim Grosbach71465ac2009-11-24 00:20:27 +000052// into t2_so_imm instructions: the 8-bit immediate is the least significant
53// bits [bits 0-7], the 4-bit shift/splat amount is the next 4 bits [bits 8-11].
Evan Cheng36173712009-06-23 17:48:47 +000054def t2_so_imm : Operand<i32>,
55 PatLeaf<(imm), [{
Evan Cheng8be2a5b2009-07-08 21:03:57 +000056 return ARM_AM::getT2SOImmVal((uint32_t)N->getZExtValue()) != -1;
57}]>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +000058
Evan Cheng36173712009-06-23 17:48:47 +000059// t2_so_imm_not - Match an immediate that is a complement
60// of a t2_so_imm.
61def t2_so_imm_not : Operand<i32>,
62 PatLeaf<(imm), [{
Evan Cheng8be2a5b2009-07-08 21:03:57 +000063 return ARM_AM::getT2SOImmVal(~((uint32_t)N->getZExtValue())) != -1;
64}], t2_so_imm_not_XFORM>;
Evan Cheng36173712009-06-23 17:48:47 +000065
66// t2_so_imm_neg - Match an immediate that is a negation of a t2_so_imm.
67def t2_so_imm_neg : Operand<i32>,
68 PatLeaf<(imm), [{
Evan Cheng8be2a5b2009-07-08 21:03:57 +000069 return ARM_AM::getT2SOImmVal(-((int)N->getZExtValue())) != -1;
70}], t2_so_imm_neg_XFORM>;
Evan Cheng36173712009-06-23 17:48:47 +000071
Jim Grosbach1afc8e22009-10-21 20:44:34 +000072// Break t2_so_imm's up into two pieces. This handles immediates with up to 16
73// bits set in them. This uses t2_so_imm2part to match and t2_so_imm2part_[12]
74// to get the first/second pieces.
75def t2_so_imm2part : Operand<i32>,
76 PatLeaf<(imm), [{
77 return ARM_AM::isT2SOImmTwoPartVal((unsigned)N->getZExtValue());
78 }]> {
79}
80
81def t2_so_imm2part_1 : SDNodeXForm<imm, [{
82 unsigned V = ARM_AM::getT2SOImmTwoPartFirst((unsigned)N->getZExtValue());
83 return CurDAG->getTargetConstant(V, MVT::i32);
84}]>;
85
86def t2_so_imm2part_2 : SDNodeXForm<imm, [{
87 unsigned V = ARM_AM::getT2SOImmTwoPartSecond((unsigned)N->getZExtValue());
88 return CurDAG->getTargetConstant(V, MVT::i32);
89}]>;
90
Jim Grosbach66e70cd2009-11-23 20:35:53 +000091def t2_so_neg_imm2part : Operand<i32>, PatLeaf<(imm), [{
92 return ARM_AM::isT2SOImmTwoPartVal(-(int)N->getZExtValue());
93 }]> {
94}
95
96def t2_so_neg_imm2part_1 : SDNodeXForm<imm, [{
97 unsigned V = ARM_AM::getT2SOImmTwoPartFirst(-(int)N->getZExtValue());
98 return CurDAG->getTargetConstant(V, MVT::i32);
99}]>;
100
101def t2_so_neg_imm2part_2 : SDNodeXForm<imm, [{
102 unsigned V = ARM_AM::getT2SOImmTwoPartSecond(-(int)N->getZExtValue());
103 return CurDAG->getTargetConstant(V, MVT::i32);
104}]>;
105
Evan Chengf7f986d2009-06-23 19:39:13 +0000106/// imm1_31 predicate - True if the 32-bit immediate is in the range [1,31].
107def imm1_31 : PatLeaf<(i32 imm), [{
108 return (int32_t)N->getZExtValue() >= 1 && (int32_t)N->getZExtValue() < 32;
109}]>;
110
Evan Cheng36173712009-06-23 17:48:47 +0000111/// imm0_4095 predicate - True if the 32-bit immediate is in the range [0.4095].
Evan Cheng815c23a2009-08-07 00:34:42 +0000112def imm0_4095 : Operand<i32>,
113 PatLeaf<(i32 imm), [{
Evan Cheng36173712009-06-23 17:48:47 +0000114 return (uint32_t)N->getZExtValue() < 4096;
115}]>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000116
117def imm0_4095_neg : PatLeaf<(i32 imm), [{
Evan Cheng36173712009-06-23 17:48:47 +0000118 return (uint32_t)(-N->getZExtValue()) < 4096;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000119}], imm_neg_XFORM>;
120
Evan Cheng809fadb2009-08-04 01:41:15 +0000121def imm0_255_neg : PatLeaf<(i32 imm), [{
122 return (uint32_t)(-N->getZExtValue()) < 255;
123}], imm_neg_XFORM>;
124
Evan Cheng532cdc52009-06-29 07:51:04 +0000125// Define Thumb2 specific addressing modes.
126
127// t2addrmode_imm12 := reg + imm12
128def t2addrmode_imm12 : Operand<i32>,
129 ComplexPattern<i32, 2, "SelectT2AddrModeImm12", []> {
130 let PrintMethod = "printT2AddrModeImm12Operand";
131 let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
132}
133
David Goodwin7938afc2009-07-24 00:16:18 +0000134// t2addrmode_imm8 := reg - imm8
Evan Cheng532cdc52009-06-29 07:51:04 +0000135def t2addrmode_imm8 : Operand<i32>,
136 ComplexPattern<i32, 2, "SelectT2AddrModeImm8", []> {
137 let PrintMethod = "printT2AddrModeImm8Operand";
138 let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
139}
140
Evan Cheng24f87d82009-07-03 00:06:39 +0000141def t2am_imm8_offset : Operand<i32>,
142 ComplexPattern<i32, 1, "SelectT2AddrModeImm8Offset", []>{
Evan Chenga90942e2009-07-02 07:28:31 +0000143 let PrintMethod = "printT2AddrModeImm8OffsetOperand";
144}
145
Evan Cheng6bc67202009-07-09 22:21:59 +0000146// t2addrmode_imm8s4 := reg +/- (imm8 << 2)
David Goodwin2af7ed82009-06-30 22:50:01 +0000147def t2addrmode_imm8s4 : Operand<i32>,
148 ComplexPattern<i32, 2, "SelectT2AddrModeImm8s4", []> {
Evan Cheng6bc67202009-07-09 22:21:59 +0000149 let PrintMethod = "printT2AddrModeImm8s4Operand";
David Goodwin2af7ed82009-06-30 22:50:01 +0000150 let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
151}
152
Evan Cheng4df2ea72009-07-09 20:40:44 +0000153// t2addrmode_so_reg := reg + (reg << imm2)
Evan Cheng532cdc52009-06-29 07:51:04 +0000154def t2addrmode_so_reg : Operand<i32>,
155 ComplexPattern<i32, 3, "SelectT2AddrModeSoReg", []> {
156 let PrintMethod = "printT2AddrModeSoRegOperand";
157 let MIOperandInfo = (ops GPR:$base, GPR:$offsreg, i32imm:$offsimm);
158}
159
160
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000161//===----------------------------------------------------------------------===//
Evan Cheng19bb7c72009-06-27 02:26:13 +0000162// Multiclass helpers...
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000163//
164
Evan Chengf7f986d2009-06-23 19:39:13 +0000165/// T2I_un_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns for a
Evan Cheng3d92dfd2009-06-25 02:08:06 +0000166/// unary operation that produces a value. These are predicable and can be
167/// changed to modify CPSR.
Johnny Chen0d810c22009-12-15 17:24:14 +0000168multiclass T2I_un_irs<bits<4> opcod, string opc, PatFrag opnode,
169 bit Cheap = 0, bit ReMat = 0> {
Evan Chengf7f986d2009-06-23 19:39:13 +0000170 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000171 def i : T2sI<(outs GPR:$dst), (ins t2_so_imm:$src), IIC_iMOVi,
Evan Cheng08540a92009-10-27 00:08:59 +0000172 opc, "\t$dst, $src",
Evan Chengf7f986d2009-06-23 19:39:13 +0000173 [(set GPR:$dst, (opnode t2_so_imm:$src))]> {
174 let isAsCheapAsAMove = Cheap;
175 let isReMaterializable = ReMat;
Johnny Chen0d810c22009-12-15 17:24:14 +0000176 let Inst{31-27} = 0b11110;
177 let Inst{25} = 0;
178 let Inst{24-21} = opcod;
179 let Inst{20} = ?; // The S bit.
180 let Inst{19-16} = 0b1111; // Rn
181 let Inst{15} = 0;
Evan Chengf7f986d2009-06-23 19:39:13 +0000182 }
183 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000184 def r : T2I<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVr,
Evan Cheng08540a92009-10-27 00:08:59 +0000185 opc, ".w\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +0000186 [(set GPR:$dst, (opnode GPR:$src))]> {
187 let Inst{31-27} = 0b11101;
188 let Inst{26-25} = 0b01;
189 let Inst{24-21} = opcod;
190 let Inst{20} = ?; // The S bit.
191 let Inst{19-16} = 0b1111; // Rn
192 let Inst{14-12} = 0b000; // imm3
193 let Inst{7-6} = 0b00; // imm2
194 let Inst{5-4} = 0b00; // type
195 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000196 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000197 def s : T2I<(outs GPR:$dst), (ins t2_so_reg:$src), IIC_iMOVsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000198 opc, ".w\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +0000199 [(set GPR:$dst, (opnode t2_so_reg:$src))]> {
200 let Inst{31-27} = 0b11101;
201 let Inst{26-25} = 0b01;
202 let Inst{24-21} = opcod;
203 let Inst{20} = ?; // The S bit.
204 let Inst{19-16} = 0b1111; // Rn
205 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000206}
207
208/// T2I_bin_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns for a
Evan Cheng3d92dfd2009-06-25 02:08:06 +0000209// binary operation that produces a value. These are predicable and can be
210/// changed to modify CPSR.
Johnny Chen0d810c22009-12-15 17:24:14 +0000211multiclass T2I_bin_irs<bits<4> opcod, string opc, PatFrag opnode,
David Goodwin87affb92009-07-27 23:34:12 +0000212 bit Commutable = 0, string wide =""> {
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000213 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000214 def ri : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000215 opc, "\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000216 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]> {
217 let Inst{31-27} = 0b11110;
218 let Inst{25} = 0;
219 let Inst{24-21} = opcod;
220 let Inst{20} = ?; // The S bit.
221 let Inst{15} = 0;
222 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000223 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000224 def rr : T2sI<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000225 opc, !strconcat(wide, "\t$dst, $lhs, $rhs"),
Evan Chengbdd679a2009-06-26 00:19:44 +0000226 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]> {
227 let isCommutable = Commutable;
Johnny Chen0d810c22009-12-15 17:24:14 +0000228 let Inst{31-27} = 0b11101;
229 let Inst{26-25} = 0b01;
230 let Inst{24-21} = opcod;
231 let Inst{20} = ?; // The S bit.
232 let Inst{14-12} = 0b000; // imm3
233 let Inst{7-6} = 0b00; // imm2
234 let Inst{5-4} = 0b00; // type
Evan Chengbdd679a2009-06-26 00:19:44 +0000235 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000236 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000237 def rs : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000238 opc, !strconcat(wide, "\t$dst, $lhs, $rhs"),
Johnny Chen0d810c22009-12-15 17:24:14 +0000239 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]> {
240 let Inst{31-27} = 0b11101;
241 let Inst{26-25} = 0b01;
242 let Inst{24-21} = opcod;
243 let Inst{20} = ?; // The S bit.
244 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000245}
246
David Goodwin87affb92009-07-27 23:34:12 +0000247/// T2I_bin_w_irs - Same as T2I_bin_irs except these operations need
248// the ".w" prefix to indicate that they are wide.
Johnny Chen0d810c22009-12-15 17:24:14 +0000249multiclass T2I_bin_w_irs<bits<4> opcod, string opc, PatFrag opnode,
250 bit Commutable = 0> :
251 T2I_bin_irs<opcod, opc, opnode, Commutable, ".w">;
David Goodwin87affb92009-07-27 23:34:12 +0000252
Evan Chengd4e2f052009-06-25 20:59:23 +0000253/// T2I_rbin_is - Same as T2I_bin_irs except the order of operands are
254/// reversed. It doesn't define the 'rr' form since it's handled by its
255/// T2I_bin_irs counterpart.
Johnny Chen0d810c22009-12-15 17:24:14 +0000256multiclass T2I_rbin_is<bits<4> opcod, string opc, PatFrag opnode> {
Evan Cheng36173712009-06-23 17:48:47 +0000257 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000258 def ri : T2I<(outs GPR:$dst), (ins GPR:$rhs, t2_so_imm:$lhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000259 opc, ".w\t$dst, $rhs, $lhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000260 [(set GPR:$dst, (opnode t2_so_imm:$lhs, GPR:$rhs))]> {
261 let Inst{31-27} = 0b11110;
262 let Inst{25} = 0;
263 let Inst{24-21} = opcod;
264 let Inst{20} = 0; // The S bit.
265 let Inst{15} = 0;
266 }
Evan Cheng36173712009-06-23 17:48:47 +0000267 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000268 def rs : T2I<(outs GPR:$dst), (ins GPR:$rhs, t2_so_reg:$lhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000269 opc, "\t$dst, $rhs, $lhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000270 [(set GPR:$dst, (opnode t2_so_reg:$lhs, GPR:$rhs))]> {
271 let Inst{31-27} = 0b11101;
272 let Inst{26-25} = 0b01;
273 let Inst{24-21} = opcod;
274 let Inst{20} = 0; // The S bit.
275 }
Evan Cheng36173712009-06-23 17:48:47 +0000276}
277
Evan Chengf7f986d2009-06-23 19:39:13 +0000278/// T2I_bin_s_irs - Similar to T2I_bin_irs except it sets the 's' bit so the
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000279/// instruction modifies the CPSR register.
280let Defs = [CPSR] in {
Johnny Chen0d810c22009-12-15 17:24:14 +0000281multiclass T2I_bin_s_irs<bits<4> opcod, string opc, PatFrag opnode,
282 bit Commutable = 0> {
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000283 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000284 def ri : T2I<(outs GPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000285 !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000286 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]> {
287 let Inst{31-27} = 0b11110;
288 let Inst{25} = 0;
289 let Inst{24-21} = opcod;
290 let Inst{20} = 1; // The S bit.
291 let Inst{15} = 0;
292 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000293 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000294 def rr : T2I<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000295 !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
Evan Chengbdd679a2009-06-26 00:19:44 +0000296 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]> {
297 let isCommutable = Commutable;
Johnny Chen0d810c22009-12-15 17:24:14 +0000298 let Inst{31-27} = 0b11101;
299 let Inst{26-25} = 0b01;
300 let Inst{24-21} = opcod;
301 let Inst{20} = 1; // The S bit.
302 let Inst{14-12} = 0b000; // imm3
303 let Inst{7-6} = 0b00; // imm2
304 let Inst{5-4} = 0b00; // type
Evan Chengbdd679a2009-06-26 00:19:44 +0000305 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000306 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000307 def rs : T2I<(outs GPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000308 !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000309 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]> {
310 let Inst{31-27} = 0b11101;
311 let Inst{26-25} = 0b01;
312 let Inst{24-21} = opcod;
313 let Inst{20} = 1; // The S bit.
314 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000315}
316}
317
Evan Chengf7f986d2009-06-23 19:39:13 +0000318/// T2I_bin_ii12rs - Defines a set of (op reg, {so_imm|imm0_4095|r|so_reg})
319/// patterns for a binary operation that produces a value.
Johnny Chen0d810c22009-12-15 17:24:14 +0000320multiclass T2I_bin_ii12rs<bits<3> op23_21, string opc, PatFrag opnode,
321 bit Commutable = 0> {
Evan Cheng36173712009-06-23 17:48:47 +0000322 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000323 def ri : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000324 opc, ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000325 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]> {
326 let Inst{31-27} = 0b11110;
327 let Inst{25} = 0;
328 let Inst{24} = 1;
329 let Inst{23-21} = op23_21;
330 let Inst{20} = 0; // The S bit.
331 let Inst{15} = 0;
332 }
Evan Cheng36173712009-06-23 17:48:47 +0000333 // 12-bit imm
David Goodwin236ccb52009-08-19 18:00:44 +0000334 def ri12 : T2sI<(outs GPR:$dst), (ins GPR:$lhs, imm0_4095:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000335 !strconcat(opc, "w"), "\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000336 [(set GPR:$dst, (opnode GPR:$lhs, imm0_4095:$rhs))]> {
337 let Inst{31-27} = 0b11110;
338 let Inst{25} = 1;
339 let Inst{24} = 0;
340 let Inst{23-21} = op23_21;
341 let Inst{20} = 0; // The S bit.
342 let Inst{15} = 0;
343 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000344 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000345 def rr : T2sI<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000346 opc, ".w\t$dst, $lhs, $rhs",
Evan Chengbdd679a2009-06-26 00:19:44 +0000347 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]> {
348 let isCommutable = Commutable;
Johnny Chen0d810c22009-12-15 17:24:14 +0000349 let Inst{31-27} = 0b11101;
350 let Inst{26-25} = 0b01;
351 let Inst{24} = 1;
352 let Inst{23-21} = op23_21;
353 let Inst{20} = 0; // The S bit.
354 let Inst{14-12} = 0b000; // imm3
355 let Inst{7-6} = 0b00; // imm2
356 let Inst{5-4} = 0b00; // type
Evan Chengbdd679a2009-06-26 00:19:44 +0000357 }
Evan Cheng36173712009-06-23 17:48:47 +0000358 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000359 def rs : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000360 opc, ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000361 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]> {
362 let Inst{31-27} = 0b11101;
Johnny Chen0d810c22009-12-15 17:24:14 +0000363 let Inst{26-25} = 0b01;
Johnny Chenc514d692010-01-08 17:41:33 +0000364 let Inst{24} = 1;
Johnny Chen0d810c22009-12-15 17:24:14 +0000365 let Inst{23-21} = op23_21;
366 let Inst{20} = 0; // The S bit.
367 }
Evan Cheng36173712009-06-23 17:48:47 +0000368}
369
Jim Grosbach71465ac2009-11-24 00:20:27 +0000370/// T2I_adde_sube_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns
371/// for a binary operation that produces a value and use and define the carry
372/// bit. It's not predicable.
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000373let Uses = [CPSR] in {
Johnny Chen0d810c22009-12-15 17:24:14 +0000374multiclass T2I_adde_sube_irs<bits<4> opcod, string opc, PatFrag opnode, bit Commutable = 0> {
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000375 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000376 def ri : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000377 opc, "\t$dst, $lhs, $rhs",
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000378 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]>,
Johnny Chen0d810c22009-12-15 17:24:14 +0000379 Requires<[IsThumb2, CarryDefIsUnused]> {
380 let Inst{31-27} = 0b11110;
381 let Inst{25} = 0;
382 let Inst{24-21} = opcod;
383 let Inst{20} = 0; // The S bit.
384 let Inst{15} = 0;
385 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000386 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000387 def rr : T2sI<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000388 opc, ".w\t$dst, $lhs, $rhs",
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000389 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]>,
Evan Chengb1b2abc2009-07-02 06:38:40 +0000390 Requires<[IsThumb2, CarryDefIsUnused]> {
Evan Chengbdd679a2009-06-26 00:19:44 +0000391 let isCommutable = Commutable;
Johnny Chen0d810c22009-12-15 17:24:14 +0000392 let Inst{31-27} = 0b11101;
393 let Inst{26-25} = 0b01;
394 let Inst{24-21} = opcod;
395 let Inst{20} = 0; // The S bit.
396 let Inst{14-12} = 0b000; // imm3
397 let Inst{7-6} = 0b00; // imm2
398 let Inst{5-4} = 0b00; // type
Evan Chengbdd679a2009-06-26 00:19:44 +0000399 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000400 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000401 def rs : T2sI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000402 opc, ".w\t$dst, $lhs, $rhs",
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000403 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]>,
Johnny Chen0d810c22009-12-15 17:24:14 +0000404 Requires<[IsThumb2, CarryDefIsUnused]> {
405 let Inst{31-27} = 0b11101;
406 let Inst{26-25} = 0b01;
407 let Inst{24-21} = opcod;
408 let Inst{20} = 0; // The S bit.
409 }
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000410 // Carry setting variants
411 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000412 def Sri : T2XI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000413 !strconcat(opc, "s\t$dst, $lhs, $rhs"),
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000414 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]>,
Evan Chengb1b2abc2009-07-02 06:38:40 +0000415 Requires<[IsThumb2, CarryDefIsUsed]> {
Johnny Chen0d810c22009-12-15 17:24:14 +0000416 let Defs = [CPSR];
417 let Inst{31-27} = 0b11110;
418 let Inst{25} = 0;
419 let Inst{24-21} = opcod;
420 let Inst{20} = 1; // The S bit.
421 let Inst{15} = 0;
422 }
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000423 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000424 def Srr : T2XI<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000425 !strconcat(opc, "s.w\t$dst, $lhs, $rhs"),
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000426 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]>,
Evan Chengb1b2abc2009-07-02 06:38:40 +0000427 Requires<[IsThumb2, CarryDefIsUsed]> {
Johnny Chen0d810c22009-12-15 17:24:14 +0000428 let Defs = [CPSR];
429 let isCommutable = Commutable;
430 let Inst{31-27} = 0b11101;
431 let Inst{26-25} = 0b01;
432 let Inst{24-21} = opcod;
433 let Inst{20} = 1; // The S bit.
434 let Inst{14-12} = 0b000; // imm3
435 let Inst{7-6} = 0b00; // imm2
436 let Inst{5-4} = 0b00; // type
Evan Chengbdd679a2009-06-26 00:19:44 +0000437 }
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000438 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000439 def Srs : T2XI<(outs GPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000440 !strconcat(opc, "s.w\t$dst, $lhs, $rhs"),
Evan Cheng9b4d26f2009-06-25 23:34:10 +0000441 [(set GPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]>,
Evan Chengb1b2abc2009-07-02 06:38:40 +0000442 Requires<[IsThumb2, CarryDefIsUsed]> {
Johnny Chen0d810c22009-12-15 17:24:14 +0000443 let Defs = [CPSR];
444 let Inst{31-27} = 0b11101;
445 let Inst{26-25} = 0b01;
446 let Inst{24-21} = opcod;
447 let Inst{20} = 1; // The S bit.
Evan Chengbdd679a2009-06-26 00:19:44 +0000448 }
Evan Cheng36173712009-06-23 17:48:47 +0000449}
450}
451
David Goodwin2f6f1132009-07-27 16:31:55 +0000452/// T2I_rbin_s_is - Same as T2I_rbin_is except sets 's' bit.
Evan Chengd4e2f052009-06-25 20:59:23 +0000453let Defs = [CPSR] in {
Johnny Chen0d810c22009-12-15 17:24:14 +0000454multiclass T2I_rbin_s_is<bits<4> opcod, string opc, PatFrag opnode> {
Evan Cheng36173712009-06-23 17:48:47 +0000455 // shifted imm
Evan Cheng6dadbee2009-08-10 02:37:24 +0000456 def ri : T2XI<(outs GPR:$dst), (ins GPR:$rhs, t2_so_imm:$lhs, cc_out:$s),
David Goodwin236ccb52009-08-19 18:00:44 +0000457 IIC_iALUi,
Evan Cheng08540a92009-10-27 00:08:59 +0000458 !strconcat(opc, "${s}.w\t$dst, $rhs, $lhs"),
Johnny Chen0d810c22009-12-15 17:24:14 +0000459 [(set GPR:$dst, (opnode t2_so_imm:$lhs, GPR:$rhs))]> {
460 let Inst{31-27} = 0b11110;
461 let Inst{25} = 0;
462 let Inst{24-21} = opcod;
463 let Inst{20} = 1; // The S bit.
464 let Inst{15} = 0;
465 }
Evan Cheng36173712009-06-23 17:48:47 +0000466 // shifted register
Evan Cheng6dadbee2009-08-10 02:37:24 +0000467 def rs : T2XI<(outs GPR:$dst), (ins GPR:$rhs, t2_so_reg:$lhs, cc_out:$s),
David Goodwin236ccb52009-08-19 18:00:44 +0000468 IIC_iALUsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000469 !strconcat(opc, "${s}\t$dst, $rhs, $lhs"),
Johnny Chen0d810c22009-12-15 17:24:14 +0000470 [(set GPR:$dst, (opnode t2_so_reg:$lhs, GPR:$rhs))]> {
471 let Inst{31-27} = 0b11101;
472 let Inst{26-25} = 0b01;
473 let Inst{24-21} = opcod;
474 let Inst{20} = 1; // The S bit.
475 }
Evan Cheng36173712009-06-23 17:48:47 +0000476}
477}
478
Evan Chengf7f986d2009-06-23 19:39:13 +0000479/// T2I_sh_ir - Defines a set of (op reg, {so_imm|r}) patterns for a shift /
480// rotate operation that produces a value.
Johnny Chen0d810c22009-12-15 17:24:14 +0000481multiclass T2I_sh_ir<bits<2> opcod, string opc, PatFrag opnode> {
Evan Chengf7f986d2009-06-23 19:39:13 +0000482 // 5-bit imm
David Goodwin236ccb52009-08-19 18:00:44 +0000483 def ri : T2sI<(outs GPR:$dst), (ins GPR:$lhs, i32imm:$rhs), IIC_iMOVsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000484 opc, ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000485 [(set GPR:$dst, (opnode GPR:$lhs, imm1_31:$rhs))]> {
486 let Inst{31-27} = 0b11101;
487 let Inst{26-21} = 0b010010;
488 let Inst{19-16} = 0b1111; // Rn
489 let Inst{5-4} = opcod;
490 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000491 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000492 def rr : T2sI<(outs GPR:$dst), (ins GPR:$lhs, GPR:$rhs), IIC_iMOVsr,
Evan Cheng08540a92009-10-27 00:08:59 +0000493 opc, ".w\t$dst, $lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000494 [(set GPR:$dst, (opnode GPR:$lhs, GPR:$rhs))]> {
495 let Inst{31-27} = 0b11111;
496 let Inst{26-23} = 0b0100;
497 let Inst{22-21} = opcod;
498 let Inst{15-12} = 0b1111;
499 let Inst{7-4} = 0b0000;
500 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000501}
Evan Cheng36173712009-06-23 17:48:47 +0000502
Johnny Chen0d810c22009-12-15 17:24:14 +0000503/// T2I_cmp_irs - Defines a set of (op r, {so_imm|r|so_reg}) cmp / test
Evan Chengf7f986d2009-06-23 19:39:13 +0000504/// patterns. Similar to T2I_bin_irs except the instruction does not produce
Evan Cheng36173712009-06-23 17:48:47 +0000505/// a explicit result, only implicitly set CPSR.
David Goodwin97eb10c2009-07-20 22:13:31 +0000506let Defs = [CPSR] in {
Johnny Chen0d810c22009-12-15 17:24:14 +0000507multiclass T2I_cmp_irs<bits<4> opcod, string opc, PatFrag opnode> {
Evan Cheng36173712009-06-23 17:48:47 +0000508 // shifted imm
David Goodwin236ccb52009-08-19 18:00:44 +0000509 def ri : T2I<(outs), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iCMPi,
Evan Cheng08540a92009-10-27 00:08:59 +0000510 opc, ".w\t$lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000511 [(opnode GPR:$lhs, t2_so_imm:$rhs)]> {
512 let Inst{31-27} = 0b11110;
513 let Inst{25} = 0;
514 let Inst{24-21} = opcod;
515 let Inst{20} = 1; // The S bit.
516 let Inst{15} = 0;
517 let Inst{11-8} = 0b1111; // Rd
518 }
Evan Chengf7f986d2009-06-23 19:39:13 +0000519 // register
David Goodwin236ccb52009-08-19 18:00:44 +0000520 def rr : T2I<(outs), (ins GPR:$lhs, GPR:$rhs), IIC_iCMPr,
Evan Cheng08540a92009-10-27 00:08:59 +0000521 opc, ".w\t$lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000522 [(opnode GPR:$lhs, GPR:$rhs)]> {
523 let Inst{31-27} = 0b11101;
524 let Inst{26-25} = 0b01;
525 let Inst{24-21} = opcod;
526 let Inst{20} = 1; // The S bit.
527 let Inst{14-12} = 0b000; // imm3
528 let Inst{11-8} = 0b1111; // Rd
529 let Inst{7-6} = 0b00; // imm2
530 let Inst{5-4} = 0b00; // type
531 }
Evan Cheng36173712009-06-23 17:48:47 +0000532 // shifted register
David Goodwin236ccb52009-08-19 18:00:44 +0000533 def rs : T2I<(outs), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iCMPsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000534 opc, ".w\t$lhs, $rhs",
Johnny Chen0d810c22009-12-15 17:24:14 +0000535 [(opnode GPR:$lhs, t2_so_reg:$rhs)]> {
536 let Inst{31-27} = 0b11101;
537 let Inst{26-25} = 0b01;
538 let Inst{24-21} = opcod;
539 let Inst{20} = 1; // The S bit.
540 let Inst{11-8} = 0b1111; // Rd
541 }
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000542}
543}
544
Evan Cheng503be112009-06-30 02:15:48 +0000545/// T2I_ld - Defines a set of (op r, {imm12|imm8|so_reg}) load patterns.
Johnny Chen0d810c22009-12-15 17:24:14 +0000546multiclass T2I_ld<bit signed, bits<2> opcod, string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +0000547 def i12 : T2Ii12<(outs GPR:$dst), (ins t2addrmode_imm12:$addr), IIC_iLoadi,
Evan Cheng08540a92009-10-27 00:08:59 +0000548 opc, ".w\t$dst, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000549 [(set GPR:$dst, (opnode t2addrmode_imm12:$addr))]> {
550 let Inst{31-27} = 0b11111;
551 let Inst{26-25} = 0b00;
552 let Inst{24} = signed;
553 let Inst{23} = 1;
554 let Inst{22-21} = opcod;
555 let Inst{20} = 1; // load
556 }
David Goodwin236ccb52009-08-19 18:00:44 +0000557 def i8 : T2Ii8 <(outs GPR:$dst), (ins t2addrmode_imm8:$addr), IIC_iLoadi,
Evan Cheng08540a92009-10-27 00:08:59 +0000558 opc, "\t$dst, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000559 [(set GPR:$dst, (opnode t2addrmode_imm8:$addr))]> {
560 let Inst{31-27} = 0b11111;
561 let Inst{26-25} = 0b00;
562 let Inst{24} = signed;
563 let Inst{23} = 0;
564 let Inst{22-21} = opcod;
565 let Inst{20} = 1; // load
566 let Inst{11} = 1;
567 // Offset: index==TRUE, wback==FALSE
568 let Inst{10} = 1; // The P bit.
569 let Inst{8} = 0; // The W bit.
570 }
David Goodwin236ccb52009-08-19 18:00:44 +0000571 def s : T2Iso <(outs GPR:$dst), (ins t2addrmode_so_reg:$addr), IIC_iLoadr,
Evan Cheng08540a92009-10-27 00:08:59 +0000572 opc, ".w\t$dst, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000573 [(set GPR:$dst, (opnode t2addrmode_so_reg:$addr))]> {
574 let Inst{31-27} = 0b11111;
575 let Inst{26-25} = 0b00;
576 let Inst{24} = signed;
577 let Inst{23} = 0;
578 let Inst{22-21} = opcod;
579 let Inst{20} = 1; // load
580 let Inst{11-6} = 0b000000;
581 }
David Goodwin236ccb52009-08-19 18:00:44 +0000582 def pci : T2Ipc <(outs GPR:$dst), (ins i32imm:$addr), IIC_iLoadi,
Evan Cheng08540a92009-10-27 00:08:59 +0000583 opc, ".w\t$dst, $addr",
Evan Cheng326d7242009-10-31 03:39:36 +0000584 [(set GPR:$dst, (opnode (ARMWrapper tconstpool:$addr)))]> {
585 let isReMaterializable = 1;
Johnny Chen0d810c22009-12-15 17:24:14 +0000586 let Inst{31-27} = 0b11111;
587 let Inst{26-25} = 0b00;
588 let Inst{24} = signed;
589 let Inst{23} = ?; // add = (U == '1')
590 let Inst{22-21} = opcod;
591 let Inst{20} = 1; // load
592 let Inst{19-16} = 0b1111; // Rn
Evan Cheng326d7242009-10-31 03:39:36 +0000593 }
Evan Cheng503be112009-06-30 02:15:48 +0000594}
595
David Goodwinbab5da12009-06-30 22:11:34 +0000596/// T2I_st - Defines a set of (op r, {imm12|imm8|so_reg}) store patterns.
Johnny Chen0d810c22009-12-15 17:24:14 +0000597multiclass T2I_st<bits<2> opcod, string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +0000598 def i12 : T2Ii12<(outs), (ins GPR:$src, t2addrmode_imm12:$addr), IIC_iStorei,
Evan Cheng08540a92009-10-27 00:08:59 +0000599 opc, ".w\t$src, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000600 [(opnode GPR:$src, t2addrmode_imm12:$addr)]> {
601 let Inst{31-27} = 0b11111;
602 let Inst{26-23} = 0b0001;
603 let Inst{22-21} = opcod;
604 let Inst{20} = 0; // !load
605 }
David Goodwin236ccb52009-08-19 18:00:44 +0000606 def i8 : T2Ii8 <(outs), (ins GPR:$src, t2addrmode_imm8:$addr), IIC_iStorei,
Evan Cheng08540a92009-10-27 00:08:59 +0000607 opc, "\t$src, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000608 [(opnode GPR:$src, t2addrmode_imm8:$addr)]> {
609 let Inst{31-27} = 0b11111;
610 let Inst{26-23} = 0b0000;
611 let Inst{22-21} = opcod;
612 let Inst{20} = 0; // !load
613 let Inst{11} = 1;
614 // Offset: index==TRUE, wback==FALSE
615 let Inst{10} = 1; // The P bit.
616 let Inst{8} = 0; // The W bit.
617 }
David Goodwin236ccb52009-08-19 18:00:44 +0000618 def s : T2Iso <(outs), (ins GPR:$src, t2addrmode_so_reg:$addr), IIC_iStorer,
Evan Cheng08540a92009-10-27 00:08:59 +0000619 opc, ".w\t$src, $addr",
Johnny Chen0d810c22009-12-15 17:24:14 +0000620 [(opnode GPR:$src, t2addrmode_so_reg:$addr)]> {
621 let Inst{31-27} = 0b11111;
622 let Inst{26-23} = 0b0000;
623 let Inst{22-21} = opcod;
624 let Inst{20} = 0; // !load
625 let Inst{11-6} = 0b000000;
626 }
David Goodwinbab5da12009-06-30 22:11:34 +0000627}
628
David Goodwin5811e5c2009-07-01 00:01:13 +0000629/// T2I_picld - Defines the PIC load pattern.
630class T2I_picld<string opc, PatFrag opnode> :
David Goodwin236ccb52009-08-19 18:00:44 +0000631 T2I<(outs GPR:$dst), (ins addrmodepc:$addr), IIC_iLoadi,
Evan Cheng08540a92009-10-27 00:08:59 +0000632 !strconcat("\n${addr:label}:\n\t", opc), "\t$dst, $addr",
David Goodwin5811e5c2009-07-01 00:01:13 +0000633 [(set GPR:$dst, (opnode addrmodepc:$addr))]>;
634
635/// T2I_picst - Defines the PIC store pattern.
636class T2I_picst<string opc, PatFrag opnode> :
David Goodwin236ccb52009-08-19 18:00:44 +0000637 T2I<(outs), (ins GPR:$src, addrmodepc:$addr), IIC_iStorer,
Evan Cheng08540a92009-10-27 00:08:59 +0000638 !strconcat("\n${addr:label}:\n\t", opc), "\t$src, $addr",
David Goodwin5811e5c2009-07-01 00:01:13 +0000639 [(opnode GPR:$src, addrmodepc:$addr)]>;
640
Evan Cheng0f994ed2009-07-03 01:43:10 +0000641
642/// T2I_unary_rrot - A unary operation with two forms: one whose operand is a
643/// register and one whose operand is a register rotated by 8/16/24.
Johnny Chen0d810c22009-12-15 17:24:14 +0000644multiclass T2I_unary_rrot<bits<3> opcod, string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +0000645 def r : T2I<(outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
Evan Cheng08540a92009-10-27 00:08:59 +0000646 opc, ".w\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +0000647 [(set GPR:$dst, (opnode GPR:$src))]> {
648 let Inst{31-27} = 0b11111;
649 let Inst{26-23} = 0b0100;
650 let Inst{22-20} = opcod;
651 let Inst{19-16} = 0b1111; // Rn
652 let Inst{15-12} = 0b1111;
653 let Inst{7} = 1;
654 let Inst{5-4} = 0b00; // rotate
655 }
David Goodwin236ccb52009-08-19 18:00:44 +0000656 def r_rot : T2I<(outs GPR:$dst), (ins GPR:$src, i32imm:$rot), IIC_iUNAsi,
Evan Cheng08540a92009-10-27 00:08:59 +0000657 opc, ".w\t$dst, $src, ror $rot",
Johnny Chen0d810c22009-12-15 17:24:14 +0000658 [(set GPR:$dst, (opnode (rotr GPR:$src, rot_imm:$rot)))]> {
659 let Inst{31-27} = 0b11111;
660 let Inst{26-23} = 0b0100;
661 let Inst{22-20} = opcod;
662 let Inst{19-16} = 0b1111; // Rn
663 let Inst{15-12} = 0b1111;
664 let Inst{7} = 1;
665 let Inst{5-4} = {?,?}; // rotate
666 }
Evan Cheng0f994ed2009-07-03 01:43:10 +0000667}
668
669/// T2I_bin_rrot - A binary operation with two forms: one whose operand is a
670/// register and one whose operand is a register rotated by 8/16/24.
Johnny Chen0d810c22009-12-15 17:24:14 +0000671multiclass T2I_bin_rrot<bits<3> opcod, string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +0000672 def rr : T2I<(outs GPR:$dst), (ins GPR:$LHS, GPR:$RHS), IIC_iALUr,
Evan Cheng08540a92009-10-27 00:08:59 +0000673 opc, "\t$dst, $LHS, $RHS",
Johnny Chen0d810c22009-12-15 17:24:14 +0000674 [(set GPR:$dst, (opnode GPR:$LHS, GPR:$RHS))]> {
675 let Inst{31-27} = 0b11111;
676 let Inst{26-23} = 0b0100;
677 let Inst{22-20} = opcod;
678 let Inst{15-12} = 0b1111;
679 let Inst{7} = 1;
680 let Inst{5-4} = 0b00; // rotate
681 }
Evan Cheng0f994ed2009-07-03 01:43:10 +0000682 def rr_rot : T2I<(outs GPR:$dst), (ins GPR:$LHS, GPR:$RHS, i32imm:$rot),
Evan Cheng08540a92009-10-27 00:08:59 +0000683 IIC_iALUsr, opc, "\t$dst, $LHS, $RHS, ror $rot",
Evan Cheng0f994ed2009-07-03 01:43:10 +0000684 [(set GPR:$dst, (opnode GPR:$LHS,
Johnny Chen0d810c22009-12-15 17:24:14 +0000685 (rotr GPR:$RHS, rot_imm:$rot)))]> {
686 let Inst{31-27} = 0b11111;
687 let Inst{26-23} = 0b0100;
688 let Inst{22-20} = opcod;
689 let Inst{15-12} = 0b1111;
690 let Inst{7} = 1;
691 let Inst{5-4} = {?,?}; // rotate
692 }
Evan Cheng0f994ed2009-07-03 01:43:10 +0000693}
694
Anton Korobeynikovac869fc2009-06-17 18:13:58 +0000695//===----------------------------------------------------------------------===//
Evan Cheng19bb7c72009-06-27 02:26:13 +0000696// Instructions
697//===----------------------------------------------------------------------===//
698
699//===----------------------------------------------------------------------===//
Evan Cheng41799702009-06-24 23:47:58 +0000700// Miscellaneous Instructions.
701//
702
Evan Cheng41799702009-06-24 23:47:58 +0000703// LEApcrel - Load a pc-relative address into a register without offending the
704// assembler.
David Goodwin236ccb52009-08-19 18:00:44 +0000705def t2LEApcrel : T2XI<(outs GPR:$dst), (ins i32imm:$label, pred:$p), IIC_iALUi,
Johnny Chen0d810c22009-12-15 17:24:14 +0000706 "adr$p.w\t$dst, #$label", []> {
707 let Inst{31-27} = 0b11110;
708 let Inst{25-24} = 0b10;
709 // Inst{23:21} = '11' (add = FALSE) or '00' (add = TRUE)
710 let Inst{22} = 0;
711 let Inst{20} = 0;
712 let Inst{19-16} = 0b1111; // Rn
713 let Inst{15} = 0;
714}
Evan Cheng3d92dfd2009-06-25 02:08:06 +0000715def t2LEApcrelJT : T2XI<(outs GPR:$dst),
Bob Wilson30ff4492009-08-21 21:58:55 +0000716 (ins i32imm:$label, nohash_imm:$id, pred:$p), IIC_iALUi,
Johnny Chen0d810c22009-12-15 17:24:14 +0000717 "adr$p.w\t$dst, #${label}_${id}", []> {
718 let Inst{31-27} = 0b11110;
719 let Inst{25-24} = 0b10;
720 // Inst{23:21} = '11' (add = FALSE) or '00' (add = TRUE)
721 let Inst{22} = 0;
722 let Inst{20} = 0;
723 let Inst{19-16} = 0b1111; // Rn
724 let Inst{15} = 0;
725}
Evan Cheng41799702009-06-24 23:47:58 +0000726
Evan Cheng815c23a2009-08-07 00:34:42 +0000727// ADD r, sp, {so_imm|i12}
David Goodwin236ccb52009-08-19 18:00:44 +0000728def t2ADDrSPi : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_imm:$imm),
Johnny Chen0d810c22009-12-15 17:24:14 +0000729 IIC_iALUi, "add", ".w\t$dst, $sp, $imm", []> {
730 let Inst{31-27} = 0b11110;
731 let Inst{25} = 0;
732 let Inst{24-21} = 0b1000;
733 let Inst{20} = ?; // The S bit.
734 let Inst{19-16} = 0b1101; // Rn = sp
735 let Inst{15} = 0;
736}
David Goodwin236ccb52009-08-19 18:00:44 +0000737def t2ADDrSPi12 : T2I<(outs GPR:$dst), (ins GPR:$sp, imm0_4095:$imm),
Johnny Chen0d810c22009-12-15 17:24:14 +0000738 IIC_iALUi, "addw", "\t$dst, $sp, $imm", []> {
739 let Inst{31-27} = 0b11110;
740 let Inst{25} = 1;
741 let Inst{24-21} = 0b0000;
742 let Inst{20} = 0; // The S bit.
743 let Inst{19-16} = 0b1101; // Rn = sp
744 let Inst{15} = 0;
745}
Evan Cheng815c23a2009-08-07 00:34:42 +0000746
747// ADD r, sp, so_reg
David Goodwin236ccb52009-08-19 18:00:44 +0000748def t2ADDrSPs : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_reg:$rhs),
Johnny Chen0d810c22009-12-15 17:24:14 +0000749 IIC_iALUsi, "add", ".w\t$dst, $sp, $rhs", []> {
750 let Inst{31-27} = 0b11101;
751 let Inst{26-25} = 0b01;
752 let Inst{24-21} = 0b1000;
753 let Inst{20} = ?; // The S bit.
754 let Inst{19-16} = 0b1101; // Rn = sp
755 let Inst{15} = 0;
756}
Evan Cheng815c23a2009-08-07 00:34:42 +0000757
758// SUB r, sp, {so_imm|i12}
David Goodwin236ccb52009-08-19 18:00:44 +0000759def t2SUBrSPi : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_imm:$imm),
Johnny Chen0d810c22009-12-15 17:24:14 +0000760 IIC_iALUi, "sub", ".w\t$dst, $sp, $imm", []> {
761 let Inst{31-27} = 0b11110;
762 let Inst{25} = 0;
763 let Inst{24-21} = 0b1101;
764 let Inst{20} = ?; // The S bit.
765 let Inst{19-16} = 0b1101; // Rn = sp
766 let Inst{15} = 0;
767}
David Goodwin236ccb52009-08-19 18:00:44 +0000768def t2SUBrSPi12 : T2I<(outs GPR:$dst), (ins GPR:$sp, imm0_4095:$imm),
Johnny Chen0d810c22009-12-15 17:24:14 +0000769 IIC_iALUi, "subw", "\t$dst, $sp, $imm", []> {
770 let Inst{31-27} = 0b11110;
771 let Inst{25} = 1;
772 let Inst{24-21} = 0b0101;
773 let Inst{20} = 0; // The S bit.
774 let Inst{19-16} = 0b1101; // Rn = sp
775 let Inst{15} = 0;
776}
Evan Cheng815c23a2009-08-07 00:34:42 +0000777
778// SUB r, sp, so_reg
David Goodwin236ccb52009-08-19 18:00:44 +0000779def t2SUBrSPs : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_reg:$rhs),
780 IIC_iALUsi,
Johnny Chen0d810c22009-12-15 17:24:14 +0000781 "sub", "\t$dst, $sp, $rhs", []> {
782 let Inst{31-27} = 0b11101;
783 let Inst{26-25} = 0b01;
784 let Inst{24-21} = 0b1101;
785 let Inst{20} = ?; // The S bit.
786 let Inst{19-16} = 0b1101; // Rn = sp
787 let Inst{15} = 0;
788}
Evan Cheng815c23a2009-08-07 00:34:42 +0000789
790// Pseudo instruction that will expand into a t2SUBrSPi + a copy.
Dan Gohman30afe012009-10-29 18:10:34 +0000791let usesCustomInserter = 1 in { // Expanded after instruction selection.
Evan Cheng815c23a2009-08-07 00:34:42 +0000792def t2SUBrSPi_ : PseudoInst<(outs GPR:$dst), (ins GPR:$sp, t2_so_imm:$imm),
Evan Cheng08540a92009-10-27 00:08:59 +0000793 NoItinerary, "@ sub.w\t$dst, $sp, $imm", []>;
Evan Cheng815c23a2009-08-07 00:34:42 +0000794def t2SUBrSPi12_ : PseudoInst<(outs GPR:$dst), (ins GPR:$sp, imm0_4095:$imm),
Evan Cheng08540a92009-10-27 00:08:59 +0000795 NoItinerary, "@ subw\t$dst, $sp, $imm", []>;
Evan Cheng815c23a2009-08-07 00:34:42 +0000796def t2SUBrSPs_ : PseudoInst<(outs GPR:$dst), (ins GPR:$sp, t2_so_reg:$rhs),
Evan Cheng08540a92009-10-27 00:08:59 +0000797 NoItinerary, "@ sub\t$dst, $sp, $rhs", []>;
Dan Gohman30afe012009-10-29 18:10:34 +0000798} // usesCustomInserter
Evan Cheng815c23a2009-08-07 00:34:42 +0000799
800
Evan Cheng41799702009-06-24 23:47:58 +0000801//===----------------------------------------------------------------------===//
Evan Cheng19bb7c72009-06-27 02:26:13 +0000802// Load / store Instructions.
803//
804
Evan Cheng532cdc52009-06-29 07:51:04 +0000805// Load
Evan Cheng2f6bfd42009-11-20 19:57:15 +0000806let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
Johnny Chen0d810c22009-12-15 17:24:14 +0000807defm t2LDR : T2I_ld<0, 0b10, "ldr", UnOpFrag<(load node:$Src)>>;
Evan Cheng532cdc52009-06-29 07:51:04 +0000808
Evan Cheng503be112009-06-30 02:15:48 +0000809// Loads with zero extension
Johnny Chen0d810c22009-12-15 17:24:14 +0000810defm t2LDRH : T2I_ld<0, 0b01, "ldrh", UnOpFrag<(zextloadi16 node:$Src)>>;
811defm t2LDRB : T2I_ld<0, 0b00, "ldrb", UnOpFrag<(zextloadi8 node:$Src)>>;
Evan Cheng532cdc52009-06-29 07:51:04 +0000812
Evan Cheng503be112009-06-30 02:15:48 +0000813// Loads with sign extension
Johnny Chen0d810c22009-12-15 17:24:14 +0000814defm t2LDRSH : T2I_ld<1, 0b01, "ldrsh", UnOpFrag<(sextloadi16 node:$Src)>>;
815defm t2LDRSB : T2I_ld<1, 0b00, "ldrsb", UnOpFrag<(sextloadi8 node:$Src)>>;
Evan Cheng532cdc52009-06-29 07:51:04 +0000816
Evan Cheng7c8d5ea2009-10-01 08:22:27 +0000817let mayLoad = 1, hasExtraDefRegAllocReq = 1 in {
Evan Cheng503be112009-06-30 02:15:48 +0000818// Load doubleword
Johnny Chen0d810c22009-12-15 17:24:14 +0000819def t2LDRDi8 : T2Ii8s4<1, 0, 1, (outs GPR:$dst1, GPR:$dst2),
Evan Cheng340684f2009-09-27 09:46:04 +0000820 (ins t2addrmode_imm8s4:$addr),
Johnny Chena9aeaea2010-01-05 22:37:28 +0000821 IIC_iLoadi, "ldrd", "\t$dst1, $addr", []>;
Johnny Chen0d810c22009-12-15 17:24:14 +0000822def t2LDRDpci : T2Ii8s4<?, ?, 1, (outs GPR:$dst1, GPR:$dst2),
Evan Cheng340684f2009-09-27 09:46:04 +0000823 (ins i32imm:$addr), IIC_iLoadi,
Johnny Chena9aeaea2010-01-05 22:37:28 +0000824 "ldrd", "\t$dst1, $addr", []> {
Johnny Chen0d810c22009-12-15 17:24:14 +0000825 let Inst{19-16} = 0b1111; // Rn
826}
Evan Cheng503be112009-06-30 02:15:48 +0000827}
828
829// zextload i1 -> zextload i8
830def : T2Pat<(zextloadi1 t2addrmode_imm12:$addr),
831 (t2LDRBi12 t2addrmode_imm12:$addr)>;
832def : T2Pat<(zextloadi1 t2addrmode_imm8:$addr),
833 (t2LDRBi8 t2addrmode_imm8:$addr)>;
834def : T2Pat<(zextloadi1 t2addrmode_so_reg:$addr),
835 (t2LDRBs t2addrmode_so_reg:$addr)>;
836def : T2Pat<(zextloadi1 (ARMWrapper tconstpool:$addr)),
837 (t2LDRBpci tconstpool:$addr)>;
838
839// extload -> zextload
840// FIXME: Reduce the number of patterns by legalizing extload to zextload
841// earlier?
842def : T2Pat<(extloadi1 t2addrmode_imm12:$addr),
843 (t2LDRBi12 t2addrmode_imm12:$addr)>;
844def : T2Pat<(extloadi1 t2addrmode_imm8:$addr),
845 (t2LDRBi8 t2addrmode_imm8:$addr)>;
846def : T2Pat<(extloadi1 t2addrmode_so_reg:$addr),
847 (t2LDRBs t2addrmode_so_reg:$addr)>;
848def : T2Pat<(extloadi1 (ARMWrapper tconstpool:$addr)),
849 (t2LDRBpci tconstpool:$addr)>;
850
851def : T2Pat<(extloadi8 t2addrmode_imm12:$addr),
852 (t2LDRBi12 t2addrmode_imm12:$addr)>;
853def : T2Pat<(extloadi8 t2addrmode_imm8:$addr),
854 (t2LDRBi8 t2addrmode_imm8:$addr)>;
855def : T2Pat<(extloadi8 t2addrmode_so_reg:$addr),
856 (t2LDRBs t2addrmode_so_reg:$addr)>;
857def : T2Pat<(extloadi8 (ARMWrapper tconstpool:$addr)),
858 (t2LDRBpci tconstpool:$addr)>;
859
860def : T2Pat<(extloadi16 t2addrmode_imm12:$addr),
861 (t2LDRHi12 t2addrmode_imm12:$addr)>;
862def : T2Pat<(extloadi16 t2addrmode_imm8:$addr),
863 (t2LDRHi8 t2addrmode_imm8:$addr)>;
864def : T2Pat<(extloadi16 t2addrmode_so_reg:$addr),
865 (t2LDRHs t2addrmode_so_reg:$addr)>;
866def : T2Pat<(extloadi16 (ARMWrapper tconstpool:$addr)),
867 (t2LDRHpci tconstpool:$addr)>;
Evan Cheng532cdc52009-06-29 07:51:04 +0000868
Evan Chenga90942e2009-07-02 07:28:31 +0000869// Indexed loads
Evan Chengd72edde2009-07-03 00:08:19 +0000870let mayLoad = 1 in {
Johnny Chen0d810c22009-12-15 17:24:14 +0000871def t2LDR_PRE : T2Iidxldst<0, 0b10, 1, 1, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000872 (ins t2addrmode_imm8:$addr),
David Goodwin236ccb52009-08-19 18:00:44 +0000873 AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000874 "ldr", "\t$dst, $addr!", "$addr.base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000875 []>;
876
Johnny Chen0d810c22009-12-15 17:24:14 +0000877def t2LDR_POST : T2Iidxldst<0, 0b10, 1, 0, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000878 (ins GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000879 AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000880 "ldr", "\t$dst, [$base], $offset", "$base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000881 []>;
882
Johnny Chen0d810c22009-12-15 17:24:14 +0000883def t2LDRB_PRE : T2Iidxldst<0, 0b00, 1, 1, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000884 (ins t2addrmode_imm8:$addr),
David Goodwin236ccb52009-08-19 18:00:44 +0000885 AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000886 "ldrb", "\t$dst, $addr!", "$addr.base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000887 []>;
Johnny Chen0d810c22009-12-15 17:24:14 +0000888def t2LDRB_POST : T2Iidxldst<0, 0b00, 1, 0, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000889 (ins GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000890 AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000891 "ldrb", "\t$dst, [$base], $offset", "$base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000892 []>;
893
Johnny Chen0d810c22009-12-15 17:24:14 +0000894def t2LDRH_PRE : T2Iidxldst<0, 0b01, 1, 1, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000895 (ins t2addrmode_imm8:$addr),
David Goodwin236ccb52009-08-19 18:00:44 +0000896 AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000897 "ldrh", "\t$dst, $addr!", "$addr.base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000898 []>;
Johnny Chen0d810c22009-12-15 17:24:14 +0000899def t2LDRH_POST : T2Iidxldst<0, 0b01, 1, 0, (outs GPR:$dst, GPR:$base_wb),
Evan Chenga90942e2009-07-02 07:28:31 +0000900 (ins GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000901 AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000902 "ldrh", "\t$dst, [$base], $offset", "$base = $base_wb",
Evan Chenga90942e2009-07-02 07:28:31 +0000903 []>;
904
Johnny Chen0d810c22009-12-15 17:24:14 +0000905def t2LDRSB_PRE : T2Iidxldst<1, 0b00, 1, 1, (outs GPR:$dst, GPR:$base_wb),
Evan Cheng40995c92009-07-02 23:16:11 +0000906 (ins t2addrmode_imm8:$addr),
David Goodwin236ccb52009-08-19 18:00:44 +0000907 AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000908 "ldrsb", "\t$dst, $addr!", "$addr.base = $base_wb",
Evan Cheng40995c92009-07-02 23:16:11 +0000909 []>;
Johnny Chen0d810c22009-12-15 17:24:14 +0000910def t2LDRSB_POST : T2Iidxldst<1, 0b00, 1, 0, (outs GPR:$dst, GPR:$base_wb),
Evan Cheng40995c92009-07-02 23:16:11 +0000911 (ins GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000912 AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000913 "ldrsb", "\t$dst, [$base], $offset", "$base = $base_wb",
Evan Cheng40995c92009-07-02 23:16:11 +0000914 []>;
915
Johnny Chen0d810c22009-12-15 17:24:14 +0000916def t2LDRSH_PRE : T2Iidxldst<1, 0b01, 1, 1, (outs GPR:$dst, GPR:$base_wb),
Evan Cheng40995c92009-07-02 23:16:11 +0000917 (ins t2addrmode_imm8:$addr),
David Goodwin236ccb52009-08-19 18:00:44 +0000918 AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000919 "ldrsh", "\t$dst, $addr!", "$addr.base = $base_wb",
Evan Cheng40995c92009-07-02 23:16:11 +0000920 []>;
Johnny Chen0d810c22009-12-15 17:24:14 +0000921def t2LDRSH_POST : T2Iidxldst<1, 0b01, 1, 0, (outs GPR:$dst, GPR:$base_wb),
Evan Cheng40995c92009-07-02 23:16:11 +0000922 (ins GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000923 AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000924 "ldrsh", "\t$dst, [$base], $offset", "$base = $base_wb",
Evan Cheng40995c92009-07-02 23:16:11 +0000925 []>;
Evan Chengd72edde2009-07-03 00:08:19 +0000926}
Evan Cheng40995c92009-07-02 23:16:11 +0000927
David Goodwinbab5da12009-06-30 22:11:34 +0000928// Store
Johnny Chen0d810c22009-12-15 17:24:14 +0000929defm t2STR : T2I_st<0b10, "str", BinOpFrag<(store node:$LHS, node:$RHS)>>;
930defm t2STRB : T2I_st<0b00, "strb", BinOpFrag<(truncstorei8 node:$LHS, node:$RHS)>>;
931defm t2STRH : T2I_st<0b01, "strh", BinOpFrag<(truncstorei16 node:$LHS, node:$RHS)>>;
David Goodwinbab5da12009-06-30 22:11:34 +0000932
David Goodwin2af7ed82009-06-30 22:50:01 +0000933// Store doubleword
Evan Cheng7c8d5ea2009-10-01 08:22:27 +0000934let mayLoad = 1, hasExtraSrcRegAllocReq = 1 in
Johnny Chen0d810c22009-12-15 17:24:14 +0000935def t2STRDi8 : T2Ii8s4<1, 0, 0, (outs),
Evan Cheng340684f2009-09-27 09:46:04 +0000936 (ins GPR:$src1, GPR:$src2, t2addrmode_imm8s4:$addr),
Johnny Chena9aeaea2010-01-05 22:37:28 +0000937 IIC_iStorer, "strd", "\t$src1, $addr", []>;
David Goodwin2af7ed82009-06-30 22:50:01 +0000938
Evan Cheng24f87d82009-07-03 00:06:39 +0000939// Indexed stores
Johnny Chen0d810c22009-12-15 17:24:14 +0000940def t2STR_PRE : T2Iidxldst<0, 0b10, 0, 1, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000941 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000942 AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000943 "str", "\t$src, [$base, $offset]!", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000944 [(set GPR:$base_wb,
945 (pre_store GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
946
Johnny Chen0d810c22009-12-15 17:24:14 +0000947def t2STR_POST : T2Iidxldst<0, 0b10, 0, 0, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000948 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000949 AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000950 "str", "\t$src, [$base], $offset", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000951 [(set GPR:$base_wb,
Jim Grosbach71465ac2009-11-24 00:20:27 +0000952 (post_store GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
Evan Cheng24f87d82009-07-03 00:06:39 +0000953
Johnny Chen0d810c22009-12-15 17:24:14 +0000954def t2STRH_PRE : T2Iidxldst<0, 0b01, 0, 1, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000955 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000956 AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000957 "strh", "\t$src, [$base, $offset]!", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000958 [(set GPR:$base_wb,
959 (pre_truncsti16 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
960
Johnny Chen0d810c22009-12-15 17:24:14 +0000961def t2STRH_POST : T2Iidxldst<0, 0b01, 0, 0, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000962 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000963 AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000964 "strh", "\t$src, [$base], $offset", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000965 [(set GPR:$base_wb,
966 (post_truncsti16 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
967
Johnny Chen0d810c22009-12-15 17:24:14 +0000968def t2STRB_PRE : T2Iidxldst<0, 0b00, 0, 1, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000969 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000970 AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000971 "strb", "\t$src, [$base, $offset]!", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000972 [(set GPR:$base_wb,
973 (pre_truncsti8 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
974
Johnny Chen0d810c22009-12-15 17:24:14 +0000975def t2STRB_POST : T2Iidxldst<0, 0b00, 0, 0, (outs GPR:$base_wb),
Evan Cheng24f87d82009-07-03 00:06:39 +0000976 (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
David Goodwin236ccb52009-08-19 18:00:44 +0000977 AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
Evan Cheng08540a92009-10-27 00:08:59 +0000978 "strb", "\t$src, [$base], $offset", "$base = $base_wb",
Evan Cheng24f87d82009-07-03 00:06:39 +0000979 [(set GPR:$base_wb,
980 (post_truncsti8 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
981
David Goodwin5811e5c2009-07-01 00:01:13 +0000982
Evan Cheng6bc67202009-07-09 22:21:59 +0000983// FIXME: ldrd / strd pre / post variants
Evan Cheng2832edf2009-07-03 00:18:36 +0000984
985//===----------------------------------------------------------------------===//
986// Load / store multiple Instructions.
987//
988
Evan Cheng7c8d5ea2009-10-01 08:22:27 +0000989let mayLoad = 1, hasExtraDefRegAllocReq = 1 in
Evan Cheng2832edf2009-07-03 00:18:36 +0000990def t2LDM : T2XI<(outs),
Evan Chengb43a20e2009-10-01 01:33:39 +0000991 (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
Johnny Chen0d810c22009-12-15 17:24:14 +0000992 IIC_iLoadm, "ldm${addr:submode}${p}${addr:wide}\t$addr, $wb", []> {
993 let Inst{31-27} = 0b11101;
994 let Inst{26-25} = 0b00;
995 let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
996 let Inst{22} = 0;
997 let Inst{21} = ?; // The W bit.
998 let Inst{20} = 1; // Load
999}
Evan Cheng2832edf2009-07-03 00:18:36 +00001000
Evan Cheng7c8d5ea2009-10-01 08:22:27 +00001001let mayStore = 1, hasExtraSrcRegAllocReq = 1 in
Evan Cheng2832edf2009-07-03 00:18:36 +00001002def t2STM : T2XI<(outs),
Evan Chengb43a20e2009-10-01 01:33:39 +00001003 (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
Johnny Chen0d810c22009-12-15 17:24:14 +00001004 IIC_iStorem, "stm${addr:submode}${p}${addr:wide}\t$addr, $wb", []> {
1005 let Inst{31-27} = 0b11101;
1006 let Inst{26-25} = 0b00;
1007 let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1008 let Inst{22} = 0;
1009 let Inst{21} = ?; // The W bit.
1010 let Inst{20} = 0; // Store
1011}
Evan Cheng2832edf2009-07-03 00:18:36 +00001012
Evan Cheng19bb7c72009-06-27 02:26:13 +00001013//===----------------------------------------------------------------------===//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001014// Move Instructions.
1015//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001016
Evan Cheng36173712009-06-23 17:48:47 +00001017let neverHasSideEffects = 1 in
David Goodwin236ccb52009-08-19 18:00:44 +00001018def t2MOVr : T2sI<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVr,
Johnny Chen0d810c22009-12-15 17:24:14 +00001019 "mov", ".w\t$dst, $src", []> {
1020 let Inst{31-27} = 0b11101;
1021 let Inst{26-25} = 0b01;
1022 let Inst{24-21} = 0b0010;
1023 let Inst{20} = ?; // The S bit.
1024 let Inst{19-16} = 0b1111; // Rn
1025 let Inst{14-12} = 0b000;
1026 let Inst{7-4} = 0b0000;
1027}
Evan Cheng36173712009-06-23 17:48:47 +00001028
Evan Cheng16c012d2009-09-28 09:14:39 +00001029// AddedComplexity to ensure isel tries t2MOVi before t2MOVi16.
1030let isReMaterializable = 1, isAsCheapAsAMove = 1, AddedComplexity = 1 in
David Goodwin236ccb52009-08-19 18:00:44 +00001031def t2MOVi : T2sI<(outs GPR:$dst), (ins t2_so_imm:$src), IIC_iMOVi,
Evan Cheng08540a92009-10-27 00:08:59 +00001032 "mov", ".w\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +00001033 [(set GPR:$dst, t2_so_imm:$src)]> {
1034 let Inst{31-27} = 0b11110;
1035 let Inst{25} = 0;
1036 let Inst{24-21} = 0b0010;
1037 let Inst{20} = ?; // The S bit.
1038 let Inst{19-16} = 0b1111; // Rn
1039 let Inst{15} = 0;
1040}
David Goodwin2dbffd42009-06-26 16:10:07 +00001041
1042let isReMaterializable = 1, isAsCheapAsAMove = 1 in
David Goodwin236ccb52009-08-19 18:00:44 +00001043def t2MOVi16 : T2I<(outs GPR:$dst), (ins i32imm:$src), IIC_iMOVi,
Evan Cheng08540a92009-10-27 00:08:59 +00001044 "movw", "\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +00001045 [(set GPR:$dst, imm0_65535:$src)]> {
1046 let Inst{31-27} = 0b11110;
1047 let Inst{25} = 1;
1048 let Inst{24-21} = 0b0010;
1049 let Inst{20} = 0; // The S bit.
1050 let Inst{15} = 0;
1051}
Evan Cheng36173712009-06-23 17:48:47 +00001052
Evan Cheng42e6ce92009-06-23 05:23:49 +00001053let Constraints = "$src = $dst" in
Evan Cheng16c012d2009-09-28 09:14:39 +00001054def t2MOVTi16 : T2I<(outs GPR:$dst), (ins GPR:$src, i32imm:$imm), IIC_iMOVi,
Evan Cheng08540a92009-10-27 00:08:59 +00001055 "movt", "\t$dst, $imm",
Evan Cheng16c012d2009-09-28 09:14:39 +00001056 [(set GPR:$dst,
Johnny Chen0d810c22009-12-15 17:24:14 +00001057 (or (and GPR:$src, 0xffff), lo16AllZero:$imm))]> {
1058 let Inst{31-27} = 0b11110;
1059 let Inst{25} = 1;
1060 let Inst{24-21} = 0b0110;
1061 let Inst{20} = 0; // The S bit.
1062 let Inst{15} = 0;
1063}
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001064
Evan Cheng89ef2852009-10-21 08:15:52 +00001065def : T2Pat<(or GPR:$src, 0xffff0000), (t2MOVTi16 GPR:$src, 0xffff)>;
1066
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001067//===----------------------------------------------------------------------===//
Evan Cheng0f994ed2009-07-03 01:43:10 +00001068// Extend Instructions.
1069//
1070
1071// Sign extenders
1072
Johnny Chen0d810c22009-12-15 17:24:14 +00001073defm t2SXTB : T2I_unary_rrot<0b100, "sxtb",
1074 UnOpFrag<(sext_inreg node:$Src, i8)>>;
1075defm t2SXTH : T2I_unary_rrot<0b000, "sxth",
1076 UnOpFrag<(sext_inreg node:$Src, i16)>>;
Evan Cheng0f994ed2009-07-03 01:43:10 +00001077
Johnny Chen0d810c22009-12-15 17:24:14 +00001078defm t2SXTAB : T2I_bin_rrot<0b100, "sxtab",
Evan Cheng0f994ed2009-07-03 01:43:10 +00001079 BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS, i8))>>;
Johnny Chen0d810c22009-12-15 17:24:14 +00001080defm t2SXTAH : T2I_bin_rrot<0b000, "sxtah",
Evan Cheng0f994ed2009-07-03 01:43:10 +00001081 BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS,i16))>>;
1082
1083// TODO: SXT(A){B|H}16
1084
1085// Zero extenders
1086
1087let AddedComplexity = 16 in {
Johnny Chen0d810c22009-12-15 17:24:14 +00001088defm t2UXTB : T2I_unary_rrot<0b101, "uxtb",
1089 UnOpFrag<(and node:$Src, 0x000000FF)>>;
1090defm t2UXTH : T2I_unary_rrot<0b001, "uxth",
1091 UnOpFrag<(and node:$Src, 0x0000FFFF)>>;
1092defm t2UXTB16 : T2I_unary_rrot<0b011, "uxtb16",
1093 UnOpFrag<(and node:$Src, 0x00FF00FF)>>;
Evan Cheng0f994ed2009-07-03 01:43:10 +00001094
1095def : T2Pat<(and (shl GPR:$Src, (i32 8)), 0xFF00FF),
1096 (t2UXTB16r_rot GPR:$Src, 24)>;
1097def : T2Pat<(and (srl GPR:$Src, (i32 8)), 0xFF00FF),
1098 (t2UXTB16r_rot GPR:$Src, 8)>;
1099
Johnny Chen0d810c22009-12-15 17:24:14 +00001100defm t2UXTAB : T2I_bin_rrot<0b101, "uxtab",
Jim Grosbach71465ac2009-11-24 00:20:27 +00001101 BinOpFrag<(add node:$LHS, (and node:$RHS, 0x00FF))>>;
Johnny Chen0d810c22009-12-15 17:24:14 +00001102defm t2UXTAH : T2I_bin_rrot<0b001, "uxtah",
Jim Grosbach71465ac2009-11-24 00:20:27 +00001103 BinOpFrag<(add node:$LHS, (and node:$RHS, 0xFFFF))>>;
Evan Cheng0f994ed2009-07-03 01:43:10 +00001104}
1105
1106//===----------------------------------------------------------------------===//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001107// Arithmetic Instructions.
1108//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001109
Johnny Chen0d810c22009-12-15 17:24:14 +00001110defm t2ADD : T2I_bin_ii12rs<0b000, "add",
1111 BinOpFrag<(add node:$LHS, node:$RHS)>, 1>;
1112defm t2SUB : T2I_bin_ii12rs<0b101, "sub",
1113 BinOpFrag<(sub node:$LHS, node:$RHS)>>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001114
Evan Cheng36173712009-06-23 17:48:47 +00001115// ADD and SUB with 's' bit set. No 12-bit immediate (T4) variants.
Johnny Chen0d810c22009-12-15 17:24:14 +00001116defm t2ADDS : T2I_bin_s_irs <0b1000, "add",
1117 BinOpFrag<(addc node:$LHS, node:$RHS)>, 1>;
1118defm t2SUBS : T2I_bin_s_irs <0b1101, "sub",
1119 BinOpFrag<(subc node:$LHS, node:$RHS)>>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001120
Johnny Chen0d810c22009-12-15 17:24:14 +00001121defm t2ADC : T2I_adde_sube_irs<0b1010, "adc",
1122 BinOpFrag<(adde node:$LHS, node:$RHS)>, 1>;
1123defm t2SBC : T2I_adde_sube_irs<0b1011, "sbc",
1124 BinOpFrag<(sube node:$LHS, node:$RHS)>>;
Evan Cheng36173712009-06-23 17:48:47 +00001125
David Goodwin3bc1afe2009-07-27 16:39:05 +00001126// RSB
Johnny Chen0d810c22009-12-15 17:24:14 +00001127defm t2RSB : T2I_rbin_is <0b1110, "rsb",
1128 BinOpFrag<(sub node:$LHS, node:$RHS)>>;
1129defm t2RSBS : T2I_rbin_s_is <0b1110, "rsb",
1130 BinOpFrag<(subc node:$LHS, node:$RHS)>>;
Evan Cheng36173712009-06-23 17:48:47 +00001131
1132// (sub X, imm) gets canonicalized to (add X, -imm). Match this form.
Evan Cheng809fadb2009-08-04 01:41:15 +00001133let AddedComplexity = 1 in
1134def : T2Pat<(add GPR:$src, imm0_255_neg:$imm),
1135 (t2SUBri GPR:$src, imm0_255_neg:$imm)>;
Evan Cheng19bb7c72009-06-27 02:26:13 +00001136def : T2Pat<(add GPR:$src, t2_so_imm_neg:$imm),
1137 (t2SUBri GPR:$src, t2_so_imm_neg:$imm)>;
1138def : T2Pat<(add GPR:$src, imm0_4095_neg:$imm),
1139 (t2SUBri12 GPR:$src, imm0_4095_neg:$imm)>;
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001140
1141
Evan Cheng36173712009-06-23 17:48:47 +00001142//===----------------------------------------------------------------------===//
Evan Chengf7f986d2009-06-23 19:39:13 +00001143// Shift and rotate Instructions.
1144//
1145
Johnny Chen0d810c22009-12-15 17:24:14 +00001146defm t2LSL : T2I_sh_ir<0b00, "lsl", BinOpFrag<(shl node:$LHS, node:$RHS)>>;
1147defm t2LSR : T2I_sh_ir<0b01, "lsr", BinOpFrag<(srl node:$LHS, node:$RHS)>>;
1148defm t2ASR : T2I_sh_ir<0b10, "asr", BinOpFrag<(sra node:$LHS, node:$RHS)>>;
1149defm t2ROR : T2I_sh_ir<0b11, "ror", BinOpFrag<(rotr node:$LHS, node:$RHS)>>;
Evan Chengf7f986d2009-06-23 19:39:13 +00001150
David Goodwin02b0e352009-09-01 18:32:09 +00001151let Uses = [CPSR] in {
David Goodwin236ccb52009-08-19 18:00:44 +00001152def t2MOVrx : T2sI<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVsi,
Evan Cheng08540a92009-10-27 00:08:59 +00001153 "rrx", "\t$dst, $src",
Johnny Chen0d810c22009-12-15 17:24:14 +00001154 [(set GPR:$dst, (ARMrrx GPR:$src))]> {
1155 let Inst{31-27} = 0b11101;
1156 let Inst{26-25} = 0b01;
1157 let Inst{24-21} = 0b0010;
1158 let Inst{20} = ?; // The S bit.
1159 let Inst{19-16} = 0b1111; // Rn
1160 let Inst{14-12} = 0b000;
1161 let Inst{7-4} = 0b0011;
1162}
David Goodwin02b0e352009-09-01 18:32:09 +00001163}
Evan Chengf7f986d2009-06-23 19:39:13 +00001164
David Goodwin7cdd24c2009-07-28 17:06:49 +00001165let Defs = [CPSR] in {
David Goodwin236ccb52009-08-19 18:00:44 +00001166def t2MOVsrl_flag : T2XI<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVsi,
Evan Cheng08540a92009-10-27 00:08:59 +00001167 "lsrs.w\t$dst, $src, #1",
Johnny Chen0d810c22009-12-15 17:24:14 +00001168 [(set GPR:$dst, (ARMsrl_flag GPR:$src))]> {
1169 let Inst{31-27} = 0b11101;
1170 let Inst{26-25} = 0b01;
1171 let Inst{24-21} = 0b0010;
1172 let Inst{20} = 1; // The S bit.
1173 let Inst{19-16} = 0b1111; // Rn
1174 let Inst{5-4} = 0b01; // Shift type.
1175 // Shift amount = Inst{14-12:7-6} = 1.
1176 let Inst{14-12} = 0b000;
1177 let Inst{7-6} = 0b01;
1178}
David Goodwin236ccb52009-08-19 18:00:44 +00001179def t2MOVsra_flag : T2XI<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVsi,
Evan Cheng08540a92009-10-27 00:08:59 +00001180 "asrs.w\t$dst, $src, #1",
Johnny Chen0d810c22009-12-15 17:24:14 +00001181 [(set GPR:$dst, (ARMsra_flag GPR:$src))]> {
1182 let Inst{31-27} = 0b11101;
1183 let Inst{26-25} = 0b01;
1184 let Inst{24-21} = 0b0010;
1185 let Inst{20} = 1; // The S bit.
1186 let Inst{19-16} = 0b1111; // Rn
1187 let Inst{5-4} = 0b10; // Shift type.
1188 // Shift amount = Inst{14-12:7-6} = 1.
1189 let Inst{14-12} = 0b000;
1190 let Inst{7-6} = 0b01;
1191}
David Goodwin7cdd24c2009-07-28 17:06:49 +00001192}
1193
Evan Chengf7f986d2009-06-23 19:39:13 +00001194//===----------------------------------------------------------------------===//
Evan Cheng36173712009-06-23 17:48:47 +00001195// Bitwise Instructions.
1196//
Anton Korobeynikovac869fc2009-06-17 18:13:58 +00001197
Johnny Chen0d810c22009-12-15 17:24:14 +00001198defm t2AND : T2I_bin_w_irs<0b0000, "and",
1199 BinOpFrag<(and node:$LHS, node:$RHS)>, 1>;
1200defm t2ORR : T2I_bin_w_irs<0b0010, "orr",
1201 BinOpFrag<(or node:$LHS, node:$RHS)>, 1>;
1202defm t2EOR : T2I_bin_w_irs<0b0100, "eor",
1203 BinOpFrag<(xor node:$LHS, node:$RHS)>, 1>;
Evan Cheng36173712009-06-23 17:48:47 +00001204
Johnny Chen0d810c22009-12-15 17:24:14 +00001205defm t2BIC : T2I_bin_w_irs<0b0001, "bic",
1206 BinOpFrag<(and node:$LHS, (not node:$RHS))>>;
Evan Cheng36173712009-06-23 17:48:47 +00001207
Evan Cheng36173712009-06-23 17:48:47 +00001208let Constraints = "$src = $dst" in
David Goodwin236ccb52009-08-19 18:00:44 +00001209def t2BFC : T2I<(outs GPR:$dst), (ins GPR:$src, bf_inv_mask_imm:$imm),
David Goodwin9a8ec822009-11-02 17:28:36 +00001210 IIC_iUNAsi, "bfc", "\t$dst, $imm",
Johnny Chen0d810c22009-12-15 17:24:14 +00001211 [(set GPR:$dst, (and GPR:$src, bf_inv_mask_imm:$imm))]> {
1212 let Inst{31-27} = 0b11110;
1213 let Inst{25} = 1;
1214 let Inst{24-20} = 0b10110;
1215 let Inst{19-16} = 0b1111; // Rn
1216 let Inst{15} = 0;
1217}
Evan Cheng36173712009-06-23 17:48:47 +00001218
Sandeep Patelbb4648a2009-10-13 18:59:48 +00001219def t2SBFX : T2I<(outs GPR:$dst), (ins GPR:$src, imm0_31:$lsb, imm0_31:$width),
Johnny Chen0d810c22009-12-15 17:24:14 +00001220 IIC_iALUi, "sbfx", "\t$dst, $src, $lsb, $width", []> {
1221 let Inst{31-27} = 0b11110;
1222 let Inst{25} = 1;
1223 let Inst{24-20} = 0b10100;
1224 let Inst{15} = 0;
1225}
Sandeep Patelbb4648a2009-10-13 18:59:48 +00001226
1227def t2UBFX : T2I<(outs GPR:$dst), (ins GPR:$src, imm0_31:$lsb, imm0_31:$width),
Johnny Chen0d810c22009-12-15 17:24:14 +00001228 IIC_iALUi, "ubfx", "\t$dst, $src, $lsb, $width", []> {
1229 let Inst{31-27} = 0b11110;
1230 let Inst{25} = 1;
1231 let Inst{24-20} = 0b11100;
1232 let Inst{15} = 0;
1233}
Sandeep Patelbb4648a2009-10-13 18:59:48 +00001234
Johnny Chenad3ead12010-02-02 19:31:58 +00001235// A8.6.18 BFI - Bitfield insert (Encoding T1)
1236// Added for disassembler with the pattern field purposely left blank.
1237// FIXME: Utilize this instruction in codgen.
1238def t2BFI : T2I<(outs GPR:$dst), (ins GPR:$src, imm0_31:$lsb, imm0_31:$width),
1239 IIC_iALUi, "bfi", "\t$dst, $src, $lsb, $width", []> {
1240 let Inst{31-27} = 0b11110;
1241 let Inst{25} = 1;
1242 let Inst{24-20} = 0b10110;
1243 let Inst{15} = 0;
1244}
Evan Cheng36173712009-06-23 17:48:47 +00001245
Johnny Chen0d810c22009-12-15 17:24:14 +00001246defm t2ORN : T2I_bin_irs<0b0011, "orn", BinOpFrag<(or node:$LHS,
1247 (not node:$RHS))>>;
Evan Cheng299ee652009-07-06 22:23:46 +00001248
1249// Prefer over of t2EORri ra, rb, -1 because mvn has 16-bit version
1250let AddedComplexity = 1 in
Johnny Chen0d810c22009-12-15 17:24:14 +00001251defm t2MVN : T2I_un_irs <0b0011, "mvn", UnOpFrag<(not node:$Src)>, 1, 1>;
Evan Cheng299ee652009-07-06 22:23:46 +00001252
1253
1254def : T2Pat<(and GPR:$src, t2_so_imm_not:$imm),
1255 (t2BICri GPR:$src, t2_so_imm_not:$imm)>;
1256
Evan Cheng04f40fa2009-08-01 06:13:52 +00001257// FIXME: Disable this pattern on Darwin to workaround an assembler bug.
David Goodwin481216a2009-07-30 21:51:41 +00001258def : T2Pat<(or GPR:$src, t2_so_imm_not:$imm),
Evan Cheng04f40fa2009-08-01 06:13:52 +00001259 (t2ORNri GPR:$src, t2_so_imm_not:$imm)>,
Evan Chengf9e5b5e2009-08-12 01:56:42 +00001260 Requires<[IsThumb2]>;
Evan Cheng299ee652009-07-06 22:23:46 +00001261
1262def : T2Pat<(t2_so_imm_not:$src),
1263 (t2MVNi t2_so_imm_not:$src)>;
1264
Evan Cheng36173712009-06-23 17:48:47 +00001265//===----------------------------------------------------------------------===//
1266// Multiply Instructions.
1267//
Evan Chengbdd679a2009-06-26 00:19:44 +00001268let isCommutable = 1 in
David Goodwin236ccb52009-08-19 18:00:44 +00001269def t2MUL: T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001270 "mul", "\t$dst, $a, $b",
Johnny Chen0d810c22009-12-15 17:24:14 +00001271 [(set GPR:$dst, (mul GPR:$a, GPR:$b))]> {
1272 let Inst{31-27} = 0b11111;
1273 let Inst{26-23} = 0b0110;
1274 let Inst{22-20} = 0b000;
1275 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1276 let Inst{7-4} = 0b0000; // Multiply
1277}
Evan Cheng36173712009-06-23 17:48:47 +00001278
David Goodwin236ccb52009-08-19 18:00:44 +00001279def t2MLA: T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c), IIC_iMAC32,
Evan Cheng08540a92009-10-27 00:08:59 +00001280 "mla", "\t$dst, $a, $b, $c",
Johnny Chen0d810c22009-12-15 17:24:14 +00001281 [(set GPR:$dst, (add (mul GPR:$a, GPR:$b), GPR:$c))]> {
1282 let Inst{31-27} = 0b11111;
1283 let Inst{26-23} = 0b0110;
1284 let Inst{22-20} = 0b000;
1285 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1286 let Inst{7-4} = 0b0000; // Multiply
1287}
Evan Cheng36173712009-06-23 17:48:47 +00001288
David Goodwin236ccb52009-08-19 18:00:44 +00001289def t2MLS: T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c), IIC_iMAC32,
Evan Cheng08540a92009-10-27 00:08:59 +00001290 "mls", "\t$dst, $a, $b, $c",
Johnny Chen0d810c22009-12-15 17:24:14 +00001291 [(set GPR:$dst, (sub GPR:$c, (mul GPR:$a, GPR:$b)))]> {
1292 let Inst{31-27} = 0b11111;
1293 let Inst{26-23} = 0b0110;
1294 let Inst{22-20} = 0b000;
1295 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1296 let Inst{7-4} = 0b0001; // Multiply and Subtract
1297}
Evan Cheng36173712009-06-23 17:48:47 +00001298
Evan Chenga5626262009-07-07 01:17:28 +00001299// Extra precision multiplies with low / high results
1300let neverHasSideEffects = 1 in {
1301let isCommutable = 1 in {
David Goodwin236ccb52009-08-19 18:00:44 +00001302def t2SMULL : T2I<(outs GPR:$ldst, GPR:$hdst), (ins GPR:$a, GPR:$b), IIC_iMUL64,
Johnny Chen0d810c22009-12-15 17:24:14 +00001303 "smull", "\t$ldst, $hdst, $a, $b", []> {
1304 let Inst{31-27} = 0b11111;
1305 let Inst{26-23} = 0b0111;
1306 let Inst{22-20} = 0b000;
1307 let Inst{7-4} = 0b0000;
1308}
Evan Chenga5626262009-07-07 01:17:28 +00001309
David Goodwin236ccb52009-08-19 18:00:44 +00001310def t2UMULL : T2I<(outs GPR:$ldst, GPR:$hdst), (ins GPR:$a, GPR:$b), IIC_iMUL64,
Johnny Chen0d810c22009-12-15 17:24:14 +00001311 "umull", "\t$ldst, $hdst, $a, $b", []> {
1312 let Inst{31-27} = 0b11111;
1313 let Inst{26-23} = 0b0111;
1314 let Inst{22-20} = 0b010;
1315 let Inst{7-4} = 0b0000;
Evan Chenga5626262009-07-07 01:17:28 +00001316}
Johnny Chen0d810c22009-12-15 17:24:14 +00001317} // isCommutable
Evan Chenga5626262009-07-07 01:17:28 +00001318
1319// Multiply + accumulate
David Goodwin236ccb52009-08-19 18:00:44 +00001320def t2SMLAL : T2I<(outs GPR:$ldst, GPR:$hdst), (ins GPR:$a, GPR:$b), IIC_iMAC64,
Johnny Chen0d810c22009-12-15 17:24:14 +00001321 "smlal", "\t$ldst, $hdst, $a, $b", []>{
1322 let Inst{31-27} = 0b11111;
1323 let Inst{26-23} = 0b0111;
1324 let Inst{22-20} = 0b100;
1325 let Inst{7-4} = 0b0000;
1326}
Evan Chenga5626262009-07-07 01:17:28 +00001327
David Goodwin236ccb52009-08-19 18:00:44 +00001328def t2UMLAL : T2I<(outs GPR:$ldst, GPR:$hdst), (ins GPR:$a, GPR:$b), IIC_iMAC64,
Johnny Chen0d810c22009-12-15 17:24:14 +00001329 "umlal", "\t$ldst, $hdst, $a, $b", []>{
1330 let Inst{31-27} = 0b11111;
1331 let Inst{26-23} = 0b0111;
1332 let Inst{22-20} = 0b110;
1333 let Inst{7-4} = 0b0000;
1334}
Evan Chenga5626262009-07-07 01:17:28 +00001335
David Goodwin236ccb52009-08-19 18:00:44 +00001336def t2UMAAL : T2I<(outs GPR:$ldst, GPR:$hdst), (ins GPR:$a, GPR:$b), IIC_iMAC64,
Johnny Chen0d810c22009-12-15 17:24:14 +00001337 "umaal", "\t$ldst, $hdst, $a, $b", []>{
1338 let Inst{31-27} = 0b11111;
1339 let Inst{26-23} = 0b0111;
1340 let Inst{22-20} = 0b110;
1341 let Inst{7-4} = 0b0110;
1342}
Evan Chenga5626262009-07-07 01:17:28 +00001343} // neverHasSideEffects
1344
1345// Most significant word multiply
David Goodwin236ccb52009-08-19 18:00:44 +00001346def t2SMMUL : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001347 "smmul", "\t$dst, $a, $b",
Johnny Chen0d810c22009-12-15 17:24:14 +00001348 [(set GPR:$dst, (mulhs GPR:$a, GPR:$b))]> {
1349 let Inst{31-27} = 0b11111;
1350 let Inst{26-23} = 0b0110;
1351 let Inst{22-20} = 0b101;
1352 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1353 let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1354}
Evan Chenga5626262009-07-07 01:17:28 +00001355
David Goodwin236ccb52009-08-19 18:00:44 +00001356def t2SMMLA : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c), IIC_iMAC32,
Evan Cheng08540a92009-10-27 00:08:59 +00001357 "smmla", "\t$dst, $a, $b, $c",
Johnny Chen0d810c22009-12-15 17:24:14 +00001358 [(set GPR:$dst, (add (mulhs GPR:$a, GPR:$b), GPR:$c))]> {
1359 let Inst{31-27} = 0b11111;
1360 let Inst{26-23} = 0b0110;
1361 let Inst{22-20} = 0b101;
1362 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1363 let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1364}
Evan Chenga5626262009-07-07 01:17:28 +00001365
1366
David Goodwin236ccb52009-08-19 18:00:44 +00001367def t2SMMLS : T2I <(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c), IIC_iMAC32,
Evan Cheng08540a92009-10-27 00:08:59 +00001368 "smmls", "\t$dst, $a, $b, $c",
Johnny Chen0d810c22009-12-15 17:24:14 +00001369 [(set GPR:$dst, (sub GPR:$c, (mulhs GPR:$a, GPR:$b)))]> {
1370 let Inst{31-27} = 0b11111;
1371 let Inst{26-23} = 0b0110;
1372 let Inst{22-20} = 0b110;
1373 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1374 let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1375}
Evan Chenga5626262009-07-07 01:17:28 +00001376
1377multiclass T2I_smul<string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +00001378 def BB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001379 !strconcat(opc, "bb"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001380 [(set GPR:$dst, (opnode (sext_inreg GPR:$a, i16),
Johnny Chen0d810c22009-12-15 17:24:14 +00001381 (sext_inreg GPR:$b, i16)))]> {
1382 let Inst{31-27} = 0b11111;
1383 let Inst{26-23} = 0b0110;
1384 let Inst{22-20} = 0b001;
1385 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1386 let Inst{7-6} = 0b00;
1387 let Inst{5-4} = 0b00;
1388 }
Evan Chenga5626262009-07-07 01:17:28 +00001389
David Goodwin236ccb52009-08-19 18:00:44 +00001390 def BT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001391 !strconcat(opc, "bt"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001392 [(set GPR:$dst, (opnode (sext_inreg GPR:$a, i16),
Johnny Chen0d810c22009-12-15 17:24:14 +00001393 (sra GPR:$b, (i32 16))))]> {
1394 let Inst{31-27} = 0b11111;
1395 let Inst{26-23} = 0b0110;
1396 let Inst{22-20} = 0b001;
1397 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1398 let Inst{7-6} = 0b00;
1399 let Inst{5-4} = 0b01;
1400 }
Evan Chenga5626262009-07-07 01:17:28 +00001401
David Goodwin236ccb52009-08-19 18:00:44 +00001402 def TB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001403 !strconcat(opc, "tb"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001404 [(set GPR:$dst, (opnode (sra GPR:$a, (i32 16)),
Johnny Chen0d810c22009-12-15 17:24:14 +00001405 (sext_inreg GPR:$b, i16)))]> {
1406 let Inst{31-27} = 0b11111;
1407 let Inst{26-23} = 0b0110;
1408 let Inst{22-20} = 0b001;
1409 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1410 let Inst{7-6} = 0b00;
1411 let Inst{5-4} = 0b10;
1412 }
Evan Chenga5626262009-07-07 01:17:28 +00001413
David Goodwin236ccb52009-08-19 18:00:44 +00001414 def TT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL32,
Evan Cheng08540a92009-10-27 00:08:59 +00001415 !strconcat(opc, "tt"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001416 [(set GPR:$dst, (opnode (sra GPR:$a, (i32 16)),
Johnny Chen0d810c22009-12-15 17:24:14 +00001417 (sra GPR:$b, (i32 16))))]> {
1418 let Inst{31-27} = 0b11111;
1419 let Inst{26-23} = 0b0110;
1420 let Inst{22-20} = 0b001;
1421 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1422 let Inst{7-6} = 0b00;
1423 let Inst{5-4} = 0b11;
1424 }
Evan Chenga5626262009-07-07 01:17:28 +00001425
David Goodwin236ccb52009-08-19 18:00:44 +00001426 def WB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL16,
Evan Cheng08540a92009-10-27 00:08:59 +00001427 !strconcat(opc, "wb"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001428 [(set GPR:$dst, (sra (opnode GPR:$a,
Johnny Chen0d810c22009-12-15 17:24:14 +00001429 (sext_inreg GPR:$b, i16)), (i32 16)))]> {
1430 let Inst{31-27} = 0b11111;
1431 let Inst{26-23} = 0b0110;
1432 let Inst{22-20} = 0b011;
1433 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1434 let Inst{7-6} = 0b00;
1435 let Inst{5-4} = 0b00;
1436 }
Evan Chenga5626262009-07-07 01:17:28 +00001437
David Goodwin236ccb52009-08-19 18:00:44 +00001438 def WT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), IIC_iMUL16,
Evan Cheng08540a92009-10-27 00:08:59 +00001439 !strconcat(opc, "wt"), "\t$dst, $a, $b",
Evan Chenga5626262009-07-07 01:17:28 +00001440 [(set GPR:$dst, (sra (opnode GPR:$a,
Johnny Chen0d810c22009-12-15 17:24:14 +00001441 (sra GPR:$b, (i32 16))), (i32 16)))]> {
1442 let Inst{31-27} = 0b11111;
1443 let Inst{26-23} = 0b0110;
1444 let Inst{22-20} = 0b011;
1445 let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1446 let Inst{7-6} = 0b00;
1447 let Inst{5-4} = 0b01;
1448 }
Evan Chenga5626262009-07-07 01:17:28 +00001449}
1450
1451
1452multiclass T2I_smla<string opc, PatFrag opnode> {
David Goodwin236ccb52009-08-19 18:00:44 +00001453 def BB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001454 !strconcat(opc, "bb"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001455 [(set GPR:$dst, (add GPR:$acc,
1456 (opnode (sext_inreg GPR:$a, i16),
Johnny Chen0d810c22009-12-15 17:24:14 +00001457 (sext_inreg GPR:$b, i16))))]> {
1458 let Inst{31-27} = 0b11111;
1459 let Inst{26-23} = 0b0110;
1460 let Inst{22-20} = 0b001;
1461 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1462 let Inst{7-6} = 0b00;
1463 let Inst{5-4} = 0b00;
1464 }
Evan Chenga5626262009-07-07 01:17:28 +00001465
David Goodwin236ccb52009-08-19 18:00:44 +00001466 def BT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001467 !strconcat(opc, "bt"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001468 [(set GPR:$dst, (add GPR:$acc, (opnode (sext_inreg GPR:$a, i16),
Johnny Chen0d810c22009-12-15 17:24:14 +00001469 (sra GPR:$b, (i32 16)))))]> {
1470 let Inst{31-27} = 0b11111;
1471 let Inst{26-23} = 0b0110;
1472 let Inst{22-20} = 0b001;
1473 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1474 let Inst{7-6} = 0b00;
1475 let Inst{5-4} = 0b01;
1476 }
Evan Chenga5626262009-07-07 01:17:28 +00001477
David Goodwin236ccb52009-08-19 18:00:44 +00001478 def TB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001479 !strconcat(opc, "tb"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001480 [(set GPR:$dst, (add GPR:$acc, (opnode (sra GPR:$a, (i32 16)),
Johnny Chen0d810c22009-12-15 17:24:14 +00001481 (sext_inreg GPR:$b, i16))))]> {
1482 let Inst{31-27} = 0b11111;
1483 let Inst{26-23} = 0b0110;
1484 let Inst{22-20} = 0b001;
1485 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1486 let Inst{7-6} = 0b00;
1487 let Inst{5-4} = 0b10;
1488 }
Evan Chenga5626262009-07-07 01:17:28 +00001489
David Goodwin236ccb52009-08-19 18:00:44 +00001490 def TT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001491 !strconcat(opc, "tt"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001492 [(set GPR:$dst, (add GPR:$acc, (opnode (sra GPR:$a, (i32 16)),
Johnny Chen0d810c22009-12-15 17:24:14 +00001493 (sra GPR:$b, (i32 16)))))]> {
1494 let Inst{31-27} = 0b11111;
1495 let Inst{26-23} = 0b0110;
1496 let Inst{22-20} = 0b001;
1497 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1498 let Inst{7-6} = 0b00;
1499 let Inst{5-4} = 0b11;
1500 }
Evan Chenga5626262009-07-07 01:17:28 +00001501
David Goodwin236ccb52009-08-19 18:00:44 +00001502 def WB : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001503 !strconcat(opc, "wb"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001504 [(set GPR:$dst, (add GPR:$acc, (sra (opnode GPR:$a,
Johnny Chen0d810c22009-12-15 17:24:14 +00001505 (sext_inreg GPR:$b, i16)), (i32 16))))]> {
1506 let Inst{31-27} = 0b11111;
1507 let Inst{26-23} = 0b0110;
1508 let Inst{22-20} = 0b011;
1509 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1510 let Inst{7-6} = 0b00;
1511 let Inst{5-4} = 0b00;
1512 }
Evan Chenga5626262009-07-07 01:17:28 +00001513
David Goodwin236ccb52009-08-19 18:00:44 +00001514 def WT : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc), IIC_iMAC16,
Evan Cheng08540a92009-10-27 00:08:59 +00001515 !strconcat(opc, "wt"), "\t$dst, $a, $b, $acc",
Evan Chenga5626262009-07-07 01:17:28 +00001516 [(set GPR:$dst, (add GPR:$acc, (sra (opnode GPR:$a,
Johnny Chen0d810c22009-12-15 17:24:14 +00001517 (sra GPR:$b, (i32 16))), (i32 16))))]> {
1518 let Inst{31-27} = 0b11111;
1519 let Inst{26-23} = 0b0110;
1520 let Inst{22-20} = 0b011;
1521 let Inst{15-12} = {?, ?, ?, ?}; // Ra
1522 let Inst{7-6} = 0b00;
1523 let Inst{5-4} = 0b01;
1524 }
Evan Chenga5626262009-07-07 01:17:28 +00001525}
1526
1527defm t2SMUL : T2I_smul<"smul", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1528defm t2SMLA : T2I_smla<"smla", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1529
1530// TODO: Halfword multiple accumulate long: SMLAL<x><y>
1531// TODO: Dual halfword multiple: SMUAD, SMUSD, SMLAD, SMLSD, SMLALD, SMLSLD
1532
Evan Cheng36173712009-06-23 17:48:47 +00001533
1534//===----------------------------------------------------------------------===//
1535// Misc. Arithmetic Instructions.
1536//
1537
Johnny Chen0d810c22009-12-15 17:24:14 +00001538class T2I_misc<bits<2> op1, bits<2> op2, dag oops, dag iops, InstrItinClass itin,
1539 string opc, string asm, list<dag> pattern>
1540 : T2I<oops, iops, itin, opc, asm, pattern> {
1541 let Inst{31-27} = 0b11111;
1542 let Inst{26-22} = 0b01010;
1543 let Inst{21-20} = op1;
1544 let Inst{15-12} = 0b1111;
1545 let Inst{7-6} = 0b10;
1546 let Inst{5-4} = op2;
1547}
Evan Cheng36173712009-06-23 17:48:47 +00001548
Johnny Chen0d810c22009-12-15 17:24:14 +00001549def t2CLZ : T2I_misc<0b11, 0b00, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1550 "clz", "\t$dst, $src", [(set GPR:$dst, (ctlz GPR:$src))]>;
Evan Cheng36173712009-06-23 17:48:47 +00001551
Jim Grosbachf1f92ff2010-01-18 19:58:49 +00001552def t2RBIT : T2I_misc<0b01, 0b10, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
Evan Chengd7da8fc2010-01-19 00:44:15 +00001553 "rbit", "\t$dst, $src",
1554 [(set GPR:$dst, (ARMrbit GPR:$src))]>;
Jim Grosbachf1f92ff2010-01-18 19:58:49 +00001555
Johnny Chen0d810c22009-12-15 17:24:14 +00001556def t2REV : T2I_misc<0b01, 0b00, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1557 "rev", ".w\t$dst, $src", [(set GPR:$dst, (bswap GPR:$src))]>;
1558
1559def t2REV16 : T2I_misc<0b01, 0b01, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1560 "rev16", ".w\t$dst, $src",
Evan Cheng36173712009-06-23 17:48:47 +00001561 [(set GPR:$dst,
1562 (or (and (srl GPR:$src, (i32 8)), 0xFF),
1563 (or (and (shl GPR:$src, (i32 8)), 0xFF00),
1564 (or (and (srl GPR:$src, (i32 8)), 0xFF0000),
1565 (and (shl GPR:$src, (i32 8)), 0xFF000000)))))]>;
1566
Johnny Chen0d810c22009-12-15 17:24:14 +00001567def t2REVSH : T2I_misc<0b01, 0b11, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1568 "revsh", ".w\t$dst, $src",
Evan Cheng36173712009-06-23 17:48:47 +00001569 [(set GPR:$dst,
1570 (sext_inreg
Evan Chengb4c98a32009-08-18 05:43:23 +00001571 (or (srl (and GPR:$src, 0xFF00), (i32 8)),
Evan Cheng36173712009-06-23 17:48:47 +00001572 (shl GPR:$src, (i32 8))), i16))]>;
1573
Evan Chengcd0ae282009-07-07 05:35:52 +00001574def t2PKHBT : T2I<(outs GPR:$dst), (ins GPR:$src1, GPR:$src2, i32imm:$shamt),
Evan Cheng08540a92009-10-27 00:08:59 +00001575 IIC_iALUsi, "pkhbt", "\t$dst, $src1, $src2, LSL $shamt",
Evan Chengcd0ae282009-07-07 05:35:52 +00001576 [(set GPR:$dst, (or (and GPR:$src1, 0xFFFF),
1577 (and (shl GPR:$src2, (i32 imm:$shamt)),
Johnny Chen0d810c22009-12-15 17:24:14 +00001578 0xFFFF0000)))]> {
1579 let Inst{31-27} = 0b11101;
1580 let Inst{26-25} = 0b01;
1581 let Inst{24-20} = 0b01100;
1582 let Inst{5} = 0; // BT form
1583 let Inst{4} = 0;
1584}
Evan Chengcd0ae282009-07-07 05:35:52 +00001585
1586// Alternate cases for PKHBT where identities eliminate some nodes.
1587def : T2Pat<(or (and GPR:$src1, 0xFFFF), (and GPR:$src2, 0xFFFF0000)),
1588 (t2PKHBT GPR:$src1, GPR:$src2, 0)>;
1589def : T2Pat<(or (and GPR:$src1, 0xFFFF), (shl GPR:$src2, imm16_31:$shamt)),
1590 (t2PKHBT GPR:$src1, GPR:$src2, imm16_31:$shamt)>;
1591
1592def t2PKHTB : T2I<(outs GPR:$dst), (ins GPR:$src1, GPR:$src2, i32imm:$shamt),
Evan Cheng08540a92009-10-27 00:08:59 +00001593 IIC_iALUsi, "pkhtb", "\t$dst, $src1, $src2, ASR $shamt",
Evan Chengcd0ae282009-07-07 05:35:52 +00001594 [(set GPR:$dst, (or (and GPR:$src1, 0xFFFF0000),
1595 (and (sra GPR:$src2, imm16_31:$shamt),
Johnny Chen0d810c22009-12-15 17:24:14 +00001596 0xFFFF)))]> {
1597 let Inst{31-27} = 0b11101;
1598 let Inst{26-25} = 0b01;
1599 let Inst{24-20} = 0b01100;
1600 let Inst{5} = 1; // TB form
1601 let Inst{4} = 0;
1602}
Evan Chengcd0ae282009-07-07 05:35:52 +00001603
1604// Alternate cases for PKHTB where identities eliminate some nodes. Note that
1605// a shift amount of 0 is *not legal* here, it is PKHBT instead.
1606def : T2Pat<(or (and GPR:$src1, 0xFFFF0000), (srl GPR:$src2, (i32 16))),
1607 (t2PKHTB GPR:$src1, GPR:$src2, 16)>;
1608def : T2Pat<(or (and GPR:$src1, 0xFFFF0000),
1609 (and (srl GPR:$src2, imm1_15:$shamt), 0xFFFF)),
1610 (t2PKHTB GPR:$src1, GPR:$src2, imm1_15:$shamt)>;
Evan Cheng36173712009-06-23 17:48:47 +00001611
1612//===----------------------------------------------------------------------===//
1613// Comparison Instructions...
1614//
1615
Johnny Chen0d810c22009-12-15 17:24:14 +00001616defm t2CMP : T2I_cmp_irs<0b1101, "cmp",
1617 BinOpFrag<(ARMcmp node:$LHS, node:$RHS)>>;
1618defm t2CMPz : T2I_cmp_irs<0b1101, "cmp",
1619 BinOpFrag<(ARMcmpZ node:$LHS, node:$RHS)>>;
Evan Cheng36173712009-06-23 17:48:47 +00001620
Jim Grosbach40e4b112010-01-22 00:08:13 +00001621//FIXME: Disable CMN, as CCodes are backwards from compare expectations
1622// Compare-to-zero still works out, just not the relationals
1623//defm t2CMN : T2I_cmp_irs<0b1000, "cmn",
1624// BinOpFrag<(ARMcmp node:$LHS,(ineg node:$RHS))>>;
Johnny Chen0d810c22009-12-15 17:24:14 +00001625defm t2CMNz : T2I_cmp_irs<0b1000, "cmn",
1626 BinOpFrag<(ARMcmpZ node:$LHS,(ineg node:$RHS))>>;
Evan Cheng36173712009-06-23 17:48:47 +00001627
Jim Grosbach40e4b112010-01-22 00:08:13 +00001628//def : T2Pat<(ARMcmp GPR:$src, t2_so_imm_neg:$imm),
1629// (t2CMNri GPR:$src, t2_so_imm_neg:$imm)>;
Evan Cheng36173712009-06-23 17:48:47 +00001630
David Goodwin8bdcbb32009-06-29 15:33:01 +00001631def : T2Pat<(ARMcmpZ GPR:$src, t2_so_imm_neg:$imm),
Jim Grosbach40e4b112010-01-22 00:08:13 +00001632 (t2CMNzri GPR:$src, t2_so_imm_neg:$imm)>;
Evan Cheng36173712009-06-23 17:48:47 +00001633
Johnny Chen0d810c22009-12-15 17:24:14 +00001634defm t2TST : T2I_cmp_irs<0b0000, "tst",
1635 BinOpFrag<(ARMcmpZ (and node:$LHS, node:$RHS), 0)>>;
1636defm t2TEQ : T2I_cmp_irs<0b0100, "teq",
1637 BinOpFrag<(ARMcmpZ (xor node:$LHS, node:$RHS), 0)>>;
Evan Cheng36173712009-06-23 17:48:47 +00001638
1639// A8.6.27 CBNZ, CBZ - Compare and branch on (non)zero.
1640// Short range conditional branch. Looks awesome for loops. Need to figure
1641// out how to use this one.
1642
Evan Cheng03137672009-07-07 20:39:03 +00001643
1644// Conditional moves
1645// FIXME: should be able to write a pattern for ARMcmov, but can't use
1646// a two-value operand where a dag node expects two operands. :(
David Goodwin236ccb52009-08-19 18:00:44 +00001647def t2MOVCCr : T2I<(outs GPR:$dst), (ins GPR:$false, GPR:$true), IIC_iCMOVr,
Evan Cheng08540a92009-10-27 00:08:59 +00001648 "mov", ".w\t$dst, $true",
Evan Cheng03137672009-07-07 20:39:03 +00001649 [/*(set GPR:$dst, (ARMcmov GPR:$false, GPR:$true, imm:$cc, CCR:$ccr))*/]>,
Johnny Chen0d810c22009-12-15 17:24:14 +00001650 RegConstraint<"$false = $dst"> {
1651 let Inst{31-27} = 0b11101;
1652 let Inst{26-25} = 0b01;
1653 let Inst{24-21} = 0b0010;
1654 let Inst{20} = 0; // The S bit.
1655 let Inst{19-16} = 0b1111; // Rn
1656 let Inst{14-12} = 0b000;
1657 let Inst{7-4} = 0b0000;
1658}
Evan Cheng03137672009-07-07 20:39:03 +00001659
David Goodwin236ccb52009-08-19 18:00:44 +00001660def t2MOVCCi : T2I<(outs GPR:$dst), (ins GPR:$false, t2_so_imm:$true),
Evan Cheng08540a92009-10-27 00:08:59 +00001661 IIC_iCMOVi, "mov", ".w\t$dst, $true",
Evan Cheng03137672009-07-07 20:39:03 +00001662[/*(set GPR:$dst, (ARMcmov GPR:$false, t2_so_imm:$true, imm:$cc, CCR:$ccr))*/]>,
Johnny Chen0d810c22009-12-15 17:24:14 +00001663 RegConstraint<"$false = $dst"> {
1664 let Inst{31-27} = 0b11110;
1665 let Inst{25} = 0;
1666 let Inst{24-21} = 0b0010;
1667 let Inst{20} = 0; // The S bit.
1668 let Inst{19-16} = 0b1111; // Rn
1669 let Inst{15} = 0;
1670}
Evan Cheng36173712009-06-23 17:48:47 +00001671
Johnny Chen0d810c22009-12-15 17:24:14 +00001672class T2I_movcc_sh<bits<2> opcod, dag oops, dag iops, InstrItinClass itin,
1673 string opc, string asm, list<dag> pattern>
1674 : T2I<oops, iops, itin, opc, asm, pattern> {
1675 let Inst{31-27} = 0b11101;
1676 let Inst{26-25} = 0b01;
1677 let Inst{24-21} = 0b0010;
1678 let Inst{20} = 0; // The S bit.
1679 let Inst{19-16} = 0b1111; // Rn
1680 let Inst{5-4} = opcod; // Shift type.
1681}
1682def t2MOVCClsl : T2I_movcc_sh<0b00, (outs GPR:$dst),
1683 (ins GPR:$false, GPR:$true, i32imm:$rhs),
1684 IIC_iCMOVsi, "lsl", ".w\t$dst, $true, $rhs", []>,
1685 RegConstraint<"$false = $dst">;
1686def t2MOVCClsr : T2I_movcc_sh<0b01, (outs GPR:$dst),
1687 (ins GPR:$false, GPR:$true, i32imm:$rhs),
1688 IIC_iCMOVsi, "lsr", ".w\t$dst, $true, $rhs", []>,
1689 RegConstraint<"$false = $dst">;
1690def t2MOVCCasr : T2I_movcc_sh<0b10, (outs GPR:$dst),
1691 (ins GPR:$false, GPR:$true, i32imm:$rhs),
1692 IIC_iCMOVsi, "asr", ".w\t$dst, $true, $rhs", []>,
1693 RegConstraint<"$false = $dst">;
1694def t2MOVCCror : T2I_movcc_sh<0b11, (outs GPR:$dst),
1695 (ins GPR:$false, GPR:$true, i32imm:$rhs),
1696 IIC_iCMOVsi, "ror", ".w\t$dst, $true, $rhs", []>,
1697 RegConstraint<"$false = $dst">;
Evan Cheng7c002f32009-08-01 01:43:45 +00001698
David Goodwinf6154702009-06-30 18:04:13 +00001699//===----------------------------------------------------------------------===//
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001700// Atomic operations intrinsics
1701//
1702
1703// memory barriers protect the atomic sequences
1704let hasSideEffects = 1 in {
1705def t2Int_MemBarrierV7 : AInoP<(outs), (ins),
1706 Pseudo, NoItinerary,
1707 "dmb", "",
Jim Grosbach6eee9032009-12-14 21:24:16 +00001708 [(ARMMemBarrierV7)]>,
Jim Grosbach2d6e2492009-12-14 19:24:11 +00001709 Requires<[IsThumb2]> {
Johnny Chen0d810c22009-12-15 17:24:14 +00001710 let Inst{31-4} = 0xF3BF8F5;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001711 // FIXME: add support for options other than a full system DMB
Johnny Chen0d810c22009-12-15 17:24:14 +00001712 let Inst{3-0} = 0b1111;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001713}
1714
1715def t2Int_SyncBarrierV7 : AInoP<(outs), (ins),
1716 Pseudo, NoItinerary,
1717 "dsb", "",
Jim Grosbach6eee9032009-12-14 21:24:16 +00001718 [(ARMSyncBarrierV7)]>,
Jim Grosbach2d6e2492009-12-14 19:24:11 +00001719 Requires<[IsThumb2]> {
Johnny Chen0d810c22009-12-15 17:24:14 +00001720 let Inst{31-4} = 0xF3BF8F4;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001721 // FIXME: add support for options other than a full system DSB
Johnny Chen0d810c22009-12-15 17:24:14 +00001722 let Inst{3-0} = 0b1111;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001723}
1724}
1725
Johnny Chen0d810c22009-12-15 17:24:14 +00001726class T2I_ldrex<bits<2> opcod, dag oops, dag iops, AddrMode am, SizeFlagVal sz,
1727 InstrItinClass itin, string opc, string asm, string cstr,
1728 list<dag> pattern, bits<4> rt2 = 0b1111>
1729 : Thumb2I<oops, iops, am, sz, itin, opc, asm, cstr, pattern> {
1730 let Inst{31-27} = 0b11101;
1731 let Inst{26-20} = 0b0001101;
1732 let Inst{11-8} = rt2;
1733 let Inst{7-6} = 0b01;
1734 let Inst{5-4} = opcod;
1735 let Inst{3-0} = 0b1111;
1736}
1737class T2I_strex<bits<2> opcod, dag oops, dag iops, AddrMode am, SizeFlagVal sz,
1738 InstrItinClass itin, string opc, string asm, string cstr,
1739 list<dag> pattern, bits<4> rt2 = 0b1111>
1740 : Thumb2I<oops, iops, am, sz, itin, opc, asm, cstr, pattern> {
1741 let Inst{31-27} = 0b11101;
1742 let Inst{26-20} = 0b0001100;
1743 let Inst{11-8} = rt2;
1744 let Inst{7-6} = 0b01;
1745 let Inst{5-4} = opcod;
1746}
1747
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001748let mayLoad = 1 in {
Johnny Chen0d810c22009-12-15 17:24:14 +00001749def t2LDREXB : T2I_ldrex<0b00, (outs GPR:$dest), (ins GPR:$ptr), AddrModeNone,
1750 Size4Bytes, NoItinerary, "ldrexb", "\t$dest, [$ptr]",
1751 "", []>;
1752def t2LDREXH : T2I_ldrex<0b01, (outs GPR:$dest), (ins GPR:$ptr), AddrModeNone,
1753 Size4Bytes, NoItinerary, "ldrexh", "\t$dest, [$ptr]",
1754 "", []>;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001755def t2LDREX : Thumb2I<(outs GPR:$dest), (ins GPR:$ptr), AddrModeNone,
Johnny Chen0d810c22009-12-15 17:24:14 +00001756 Size4Bytes, NoItinerary,
1757 "ldrex", "\t$dest, [$ptr]", "",
1758 []> {
1759 let Inst{31-27} = 0b11101;
1760 let Inst{26-20} = 0b0000101;
1761 let Inst{11-8} = 0b1111;
1762 let Inst{7-0} = 0b00000000; // imm8 = 0
1763}
1764def t2LDREXD : T2I_ldrex<0b11, (outs GPR:$dest, GPR:$dest2), (ins GPR:$ptr),
1765 AddrModeNone, Size4Bytes, NoItinerary,
1766 "ldrexd", "\t$dest, $dest2, [$ptr]", "",
1767 [], {?, ?, ?, ?}>;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001768}
1769
Jim Grosbach724d7a12009-12-16 19:44:06 +00001770let mayStore = 1, Constraints = "@earlyclobber $success" in {
Johnny Chen0d810c22009-12-15 17:24:14 +00001771def t2STREXB : T2I_strex<0b00, (outs GPR:$success), (ins GPR:$src, GPR:$ptr),
1772 AddrModeNone, Size4Bytes, NoItinerary,
1773 "strexb", "\t$success, $src, [$ptr]", "", []>;
1774def t2STREXH : T2I_strex<0b01, (outs GPR:$success), (ins GPR:$src, GPR:$ptr),
1775 AddrModeNone, Size4Bytes, NoItinerary,
1776 "strexh", "\t$success, $src, [$ptr]", "", []>;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001777def t2STREX : Thumb2I<(outs GPR:$success), (ins GPR:$src, GPR:$ptr),
Johnny Chen0d810c22009-12-15 17:24:14 +00001778 AddrModeNone, Size4Bytes, NoItinerary,
1779 "strex", "\t$success, $src, [$ptr]", "",
1780 []> {
1781 let Inst{31-27} = 0b11101;
1782 let Inst{26-20} = 0b0000100;
1783 let Inst{7-0} = 0b00000000; // imm8 = 0
1784}
1785def t2STREXD : T2I_strex<0b11, (outs GPR:$success),
1786 (ins GPR:$src, GPR:$src2, GPR:$ptr),
1787 AddrModeNone, Size4Bytes, NoItinerary,
1788 "strexd", "\t$success, $src, $src2, [$ptr]", "", [],
1789 {?, ?, ?, ?}>;
Jim Grosbachefbc1f02009-12-14 18:56:47 +00001790}
1791
1792//===----------------------------------------------------------------------===//
David Goodwin41afec22009-07-08 16:09:28 +00001793// TLS Instructions
1794//
1795
1796// __aeabi_read_tp preserves the registers r1-r3.
1797let isCall = 1,
1798 Defs = [R0, R12, LR, CPSR] in {
David Goodwincfd67652009-08-06 16:52:47 +00001799 def t2TPsoft : T2XI<(outs), (ins), IIC_Br,
Evan Cheng08540a92009-10-27 00:08:59 +00001800 "bl\t__aeabi_read_tp",
Johnny Chen0d810c22009-12-15 17:24:14 +00001801 [(set R0, ARMthread_pointer)]> {
1802 let Inst{31-27} = 0b11110;
1803 let Inst{15-14} = 0b11;
1804 let Inst{12} = 1;
1805 }
David Goodwin41afec22009-07-08 16:09:28 +00001806}
1807
1808//===----------------------------------------------------------------------===//
Jim Grosbachcc6e66a2009-08-11 19:42:21 +00001809// SJLJ Exception handling intrinsics
Jim Grosbach207a4ba2009-08-13 15:11:43 +00001810// eh_sjlj_setjmp() is an instruction sequence to store the return
Jim Grosbachcc6e66a2009-08-11 19:42:21 +00001811// address and save #0 in R0 for the non-longjmp case.
1812// Since by its nature we may be coming from some other function to get
1813// here, and we're using the stack frame for the containing function to
1814// save/restore registers, we can't keep anything live in regs across
1815// the eh_sjlj_setjmp(), else it will almost certainly have been tromped upon
1816// when we get here from a longjmp(). We force everthing out of registers
1817// except for our own input by listing the relevant registers in Defs. By
1818// doing so, we also cause the prologue/epilogue code to actively preserve
1819// all of the callee-saved resgisters, which is exactly what we want.
Jim Grosbach8d96fc12010-02-08 23:22:00 +00001820// The current SP is passed in $val, and we reuse the reg as a scratch.
1821let Defs =
Jim Grosbach3990e392009-08-13 16:59:44 +00001822 [ R0, R1, R2, R3, R4, R5, R6, R7, R8, R9, R10, R11, R12, LR, D0,
1823 D1, D2, D3, D4, D5, D6, D7, D8, D9, D10, D11, D12, D13, D14, D15,
Jim Grosbachcc6e66a2009-08-11 19:42:21 +00001824 D16, D17, D18, D19, D20, D21, D22, D23, D24, D25, D26, D27, D28, D29, D30,
1825 D31 ] in {
Jim Grosbach8d96fc12010-02-08 23:22:00 +00001826 def t2Int_eh_sjlj_setjmp : Thumb2XI<(outs), (ins GPR:$src, tGPR:$val),
Jim Grosbachcc6e66a2009-08-11 19:42:21 +00001827 AddrModeNone, SizeSpecial, NoItinerary,
Jim Grosbach8d96fc12010-02-08 23:22:00 +00001828 "str\t$val, [$src, #8]\t@ begin eh.setjmp\n"
1829 "\tmov\t$val, pc\n"
1830 "\tadds\t$val, #9\n"
1831 "\tstr\t$val, [$src, #4]\n"
Evan Cheng08540a92009-10-27 00:08:59 +00001832 "\tmovs\tr0, #0\n"
1833 "\tb\t1f\n"
Jim Grosbach8d96fc12010-02-08 23:22:00 +00001834 "\tmovs\tr0, #1\t@ end eh.setjmp\n"
Jim Grosbachdd4f75b2009-08-13 15:12:16 +00001835 "1:", "",
Jim Grosbach8d96fc12010-02-08 23:22:00 +00001836 [(set R0, (ARMeh_sjlj_setjmp GPR:$src, tGPR:$val))]>;
Jim Grosbachcc6e66a2009-08-11 19:42:21 +00001837}
1838
1839
1840
1841//===----------------------------------------------------------------------===//
David Goodwinf6154702009-06-30 18:04:13 +00001842// Control-Flow Instructions
1843//
1844
Evan Chengad877c82009-07-09 22:58:39 +00001845// FIXME: remove when we have a way to marking a MI with these properties.
1846// FIXME: $dst1 should be a def. But the extra ops must be in the end of the
1847// operand list.
1848// FIXME: Should pc be an implicit operand like PICADD, etc?
Evan Cheng7c8d5ea2009-10-01 08:22:27 +00001849let isReturn = 1, isTerminator = 1, isBarrier = 1, mayLoad = 1,
1850 hasExtraDefRegAllocReq = 1 in
Evan Chengad877c82009-07-09 22:58:39 +00001851 def t2LDM_RET : T2XI<(outs),
Evan Chengb43a20e2009-10-01 01:33:39 +00001852 (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
Evan Cheng08540a92009-10-27 00:08:59 +00001853 IIC_Br, "ldm${addr:submode}${p}${addr:wide}\t$addr, $wb",
Johnny Chen0d810c22009-12-15 17:24:14 +00001854 []> {
1855 let Inst{31-27} = 0b11101;
1856 let Inst{26-25} = 0b00;
1857 let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1858 let Inst{22} = 0;
1859 let Inst{21} = ?; // The W bit.
1860 let Inst{20} = 1; // Load
1861}
Evan Chengad877c82009-07-09 22:58:39 +00001862
David Goodwinf6154702009-06-30 18:04:13 +00001863let isBranch = 1, isTerminator = 1, isBarrier = 1 in {
1864let isPredicable = 1 in
David Goodwincfd67652009-08-06 16:52:47 +00001865def t2B : T2XI<(outs), (ins brtarget:$target), IIC_Br,
Evan Cheng08540a92009-10-27 00:08:59 +00001866 "b.w\t$target",
Johnny Chen0d810c22009-12-15 17:24:14 +00001867 [(br bb:$target)]> {
1868 let Inst{31-27} = 0b11110;
1869 let Inst{15-14} = 0b10;
1870 let Inst{12} = 1;
1871}
David Goodwinf6154702009-06-30 18:04:13 +00001872
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001873let isNotDuplicable = 1, isIndirectBranch = 1 in {
Evan Cheng6e2ebc92009-07-25 00:33:29 +00001874def t2BR_JT :
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001875 T2JTI<(outs),
1876 (ins GPR:$target, GPR:$index, jt2block_operand:$jt, i32imm:$id),
Evan Cheng08540a92009-10-27 00:08:59 +00001877 IIC_Br, "mov\tpc, $target\n$jt",
Johnny Chen0d810c22009-12-15 17:24:14 +00001878 [(ARMbr2jt GPR:$target, GPR:$index, tjumptable:$jt, imm:$id)]> {
1879 let Inst{31-27} = 0b11101;
1880 let Inst{26-20} = 0b0100100;
1881 let Inst{19-16} = 0b1111;
1882 let Inst{14-12} = 0b000;
1883 let Inst{11-8} = 0b1111; // Rd = pc
1884 let Inst{7-4} = 0b0000;
1885}
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001886
Evan Cheng04f40fa2009-08-01 06:13:52 +00001887// FIXME: Add a non-pc based case that can be predicated.
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001888def t2TBB :
Evan Cheng04f40fa2009-08-01 06:13:52 +00001889 T2JTI<(outs),
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001890 (ins tb_addrmode:$index, jt2block_operand:$jt, i32imm:$id),
Johnny Chen0d810c22009-12-15 17:24:14 +00001891 IIC_Br, "tbb\t$index\n$jt", []> {
1892 let Inst{31-27} = 0b11101;
1893 let Inst{26-20} = 0b0001101;
1894 let Inst{19-16} = 0b1111; // Rn = pc (table follows this instruction)
1895 let Inst{15-8} = 0b11110000;
1896 let Inst{7-4} = 0b0000; // B form
1897}
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001898
1899def t2TBH :
Evan Cheng04f40fa2009-08-01 06:13:52 +00001900 T2JTI<(outs),
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001901 (ins tb_addrmode:$index, jt2block_operand:$jt, i32imm:$id),
Johnny Chen0d810c22009-12-15 17:24:14 +00001902 IIC_Br, "tbh\t$index\n$jt", []> {
1903 let Inst{31-27} = 0b11101;
1904 let Inst{26-20} = 0b0001101;
1905 let Inst{19-16} = 0b1111; // Rn = pc (table follows this instruction)
1906 let Inst{15-8} = 0b11110000;
1907 let Inst{7-4} = 0b0001; // H form
1908}
Evan Cheng1b2b3e22009-07-29 02:18:14 +00001909} // isNotDuplicable, isIndirectBranch
1910
David Goodwin13d2f4e2009-06-30 19:50:22 +00001911} // isBranch, isTerminator, isBarrier
David Goodwinf6154702009-06-30 18:04:13 +00001912
1913// FIXME: should be able to write a pattern for ARMBrcond, but can't use
1914// a two-value operand where a dag node expects two operands. :(
1915let isBranch = 1, isTerminator = 1 in
David Goodwincfd67652009-08-06 16:52:47 +00001916def t2Bcc : T2I<(outs), (ins brtarget:$target), IIC_Br,
Evan Cheng08540a92009-10-27 00:08:59 +00001917 "b", ".w\t$target",
Johnny Chen0d810c22009-12-15 17:24:14 +00001918 [/*(ARMbrcond bb:$target, imm:$cc)*/]> {
1919 let Inst{31-27} = 0b11110;
1920 let Inst{15-14} = 0b10;
1921 let Inst{12} = 0;
1922}
Evan Cheng36173712009-06-23 17:48:47 +00001923
Evan Chengd5b67fa2009-07-10 01:54:42 +00001924
1925// IT block
1926def t2IT : Thumb2XI<(outs), (ins it_pred:$cc, it_mask:$mask),
David Goodwin236ccb52009-08-19 18:00:44 +00001927 AddrModeNone, Size2Bytes, IIC_iALUx,
Johnny Chen0d810c22009-12-15 17:24:14 +00001928 "it$mask\t$cc", "", []> {
1929 // 16-bit instruction.
Johnny Chenaa640d32009-12-16 02:32:54 +00001930 let Inst{31-16} = 0x0000;
Johnny Chen0d810c22009-12-15 17:24:14 +00001931 let Inst{15-8} = 0b10111111;
1932}
Evan Chengd5b67fa2009-07-10 01:54:42 +00001933
Evan Cheng36173712009-06-23 17:48:47 +00001934//===----------------------------------------------------------------------===//
1935// Non-Instruction Patterns
1936//
1937
Jim Grosbach1afc8e22009-10-21 20:44:34 +00001938// Two piece so_imms.
1939def : T2Pat<(or GPR:$LHS, t2_so_imm2part:$RHS),
1940 (t2ORRri (t2ORRri GPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
1941 (t2_so_imm2part_2 imm:$RHS))>;
1942def : T2Pat<(xor GPR:$LHS, t2_so_imm2part:$RHS),
1943 (t2EORri (t2EORri GPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
1944 (t2_so_imm2part_2 imm:$RHS))>;
1945def : T2Pat<(add GPR:$LHS, t2_so_imm2part:$RHS),
1946 (t2ADDri (t2ADDri GPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
1947 (t2_so_imm2part_2 imm:$RHS))>;
Jim Grosbach66e70cd2009-11-23 20:35:53 +00001948def : T2Pat<(add GPR:$LHS, t2_so_neg_imm2part:$RHS),
1949 (t2SUBri (t2SUBri GPR:$LHS, (t2_so_neg_imm2part_1 imm:$RHS)),
1950 (t2_so_neg_imm2part_2 imm:$RHS))>;
Jim Grosbach1afc8e22009-10-21 20:44:34 +00001951
Evan Cheng16c012d2009-09-28 09:14:39 +00001952// 32-bit immediate using movw + movt.
1953// This is a single pseudo instruction to make it re-materializable. Remove
1954// when we can do generalized remat.
1955let isReMaterializable = 1 in
1956def t2MOVi32imm : T2Ix2<(outs GPR:$dst), (ins i32imm:$src), IIC_iMOVi,
Evan Cheng08540a92009-10-27 00:08:59 +00001957 "movw", "\t$dst, ${src:lo16}\n\tmovt${p}\t$dst, ${src:hi16}",
Evan Cheng16c012d2009-09-28 09:14:39 +00001958 [(set GPR:$dst, (i32 imm:$src))]>;
Evan Cheng7921e582009-11-06 23:52:48 +00001959
Anton Korobeynikova414f362009-11-24 00:44:37 +00001960// ConstantPool, GlobalAddress, and JumpTable
1961def : T2Pat<(ARMWrapper tglobaladdr :$dst), (t2LEApcrel tglobaladdr :$dst)>,
1962 Requires<[IsThumb2, DontUseMovt]>;
1963def : T2Pat<(ARMWrapper tconstpool :$dst), (t2LEApcrel tconstpool :$dst)>;
1964def : T2Pat<(ARMWrapper tglobaladdr :$dst), (t2MOVi32imm tglobaladdr :$dst)>,
1965 Requires<[IsThumb2, UseMovt]>;
1966
1967def : T2Pat<(ARMWrapperJT tjumptable:$dst, imm:$id),
1968 (t2LEApcrelJT tjumptable:$dst, imm:$id)>;
1969
Evan Cheng7921e582009-11-06 23:52:48 +00001970// Pseudo instruction that combines ldr from constpool and add pc. This should
1971// be expanded into two instructions late to allow if-conversion and
1972// scheduling.
Evan Cheng2f6bfd42009-11-20 19:57:15 +00001973let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
Evan Cheng7921e582009-11-06 23:52:48 +00001974def t2LDRpci_pic : PseudoInst<(outs GPR:$dst), (ins i32imm:$addr, pclabel:$cp),
1975 NoItinerary, "@ ldr.w\t$dst, $addr\n$cp:\n\tadd\t$dst, pc",
1976 [(set GPR:$dst, (ARMpic_add (load (ARMWrapper tconstpool:$addr)),
1977 imm:$cp))]>,
1978 Requires<[IsThumb2]>;