ARMInstrThumb2.td revision 55c134a26188291f60c44d027a837f05d797194f
1//===- 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//===----------------------------------------------------------------------===//
13
14// IT block predicate field
15def it_pred : Operand<i32> {
16  let PrintMethod = "printMandatoryPredicateOperand";
17}
18
19// IT block condition mask
20def it_mask : Operand<i32> {
21  let PrintMethod = "printThumbITMask";
22}
23
24// Table branch address
25def tb_addrmode : Operand<i32> {
26  let PrintMethod = "printTBAddrMode";
27}
28
29// 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
32                ComplexPattern<i32, 2, "SelectT2ShifterOperandReg",
33                               [shl,srl,sra,rotr]> {
34  let PrintMethod = "printT2SOOperand";
35  let MIOperandInfo = (ops rGPR, i32imm);
36}
37
38// t2_so_imm_not_XFORM - Return the complement of a t2_so_imm value
39def t2_so_imm_not_XFORM : SDNodeXForm<imm, [{
40  return CurDAG->getTargetConstant(~((uint32_t)N->getZExtValue()), MVT::i32);
41}]>;
42
43// t2_so_imm_neg_XFORM - Return the negation of a t2_so_imm value
44def t2_so_imm_neg_XFORM : SDNodeXForm<imm, [{
45  return CurDAG->getTargetConstant(-((int)N->getZExtValue()), MVT::i32);
46}]>;
47
48// 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
52// 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].
54def t2_so_imm : Operand<i32>, PatLeaf<(imm), [{ return Pred_t2_so_imm(N); }]>;
55
56// t2_so_imm_not - Match an immediate that is a complement
57// of a t2_so_imm.
58def t2_so_imm_not : Operand<i32>,
59                    PatLeaf<(imm), [{
60  return ARM_AM::getT2SOImmVal(~((uint32_t)N->getZExtValue())) != -1;
61}], t2_so_imm_not_XFORM>;
62
63// t2_so_imm_neg - Match an immediate that is a negation of a t2_so_imm.
64def t2_so_imm_neg : Operand<i32>,
65                    PatLeaf<(imm), [{
66  return ARM_AM::getT2SOImmVal(-((int)N->getZExtValue())) != -1;
67}], t2_so_imm_neg_XFORM>;
68
69// Break t2_so_imm's up into two pieces.  This handles immediates with up to 16
70// bits set in them.  This uses t2_so_imm2part to match and t2_so_imm2part_[12]
71// to get the first/second pieces.
72def t2_so_imm2part : Operand<i32>,
73                  PatLeaf<(imm), [{
74      return ARM_AM::isT2SOImmTwoPartVal((unsigned)N->getZExtValue());
75    }]> {
76}
77
78def t2_so_imm2part_1 : SDNodeXForm<imm, [{
79  unsigned V = ARM_AM::getT2SOImmTwoPartFirst((unsigned)N->getZExtValue());
80  return CurDAG->getTargetConstant(V, MVT::i32);
81}]>;
82
83def t2_so_imm2part_2 : SDNodeXForm<imm, [{
84  unsigned V = ARM_AM::getT2SOImmTwoPartSecond((unsigned)N->getZExtValue());
85  return CurDAG->getTargetConstant(V, MVT::i32);
86}]>;
87
88def t2_so_neg_imm2part : Operand<i32>, PatLeaf<(imm), [{
89      return ARM_AM::isT2SOImmTwoPartVal(-(int)N->getZExtValue());
90    }]> {
91}
92
93def t2_so_neg_imm2part_1 : SDNodeXForm<imm, [{
94  unsigned V = ARM_AM::getT2SOImmTwoPartFirst(-(int)N->getZExtValue());
95  return CurDAG->getTargetConstant(V, MVT::i32);
96}]>;
97
98def t2_so_neg_imm2part_2 : SDNodeXForm<imm, [{
99  unsigned V = ARM_AM::getT2SOImmTwoPartSecond(-(int)N->getZExtValue());
100  return CurDAG->getTargetConstant(V, MVT::i32);
101}]>;
102
103/// imm1_31 predicate - True if the 32-bit immediate is in the range [1,31].
104def imm1_31 : PatLeaf<(i32 imm), [{
105  return (int32_t)N->getZExtValue() >= 1 && (int32_t)N->getZExtValue() < 32;
106}]>;
107
108/// imm0_4095 predicate - True if the 32-bit immediate is in the range [0.4095].
109def imm0_4095 : Operand<i32>,
110                PatLeaf<(i32 imm), [{
111  return (uint32_t)N->getZExtValue() < 4096;
112}]>;
113
114def imm0_4095_neg : PatLeaf<(i32 imm), [{
115 return (uint32_t)(-N->getZExtValue()) < 4096;
116}], imm_neg_XFORM>;
117
118def imm0_255_neg : PatLeaf<(i32 imm), [{
119  return (uint32_t)(-N->getZExtValue()) < 255;
120}], imm_neg_XFORM>;
121
122def imm0_255_not : PatLeaf<(i32 imm), [{
123  return (uint32_t)(~N->getZExtValue()) < 255;
124}], imm_comp_XFORM>;
125
126// Define Thumb2 specific addressing modes.
127
128// t2addrmode_imm12  := reg + imm12
129def t2addrmode_imm12 : Operand<i32>,
130                       ComplexPattern<i32, 2, "SelectT2AddrModeImm12", []> {
131  let PrintMethod = "printT2AddrModeImm12Operand";
132  let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
133}
134
135// t2addrmode_imm8  := reg +/- imm8
136def t2addrmode_imm8 : Operand<i32>,
137                      ComplexPattern<i32, 2, "SelectT2AddrModeImm8", []> {
138  let PrintMethod = "printT2AddrModeImm8Operand";
139  let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
140}
141
142def t2am_imm8_offset : Operand<i32>,
143                       ComplexPattern<i32, 1, "SelectT2AddrModeImm8Offset", []>{
144  let PrintMethod = "printT2AddrModeImm8OffsetOperand";
145}
146
147// t2addrmode_imm8s4  := reg +/- (imm8 << 2)
148def t2addrmode_imm8s4 : Operand<i32>,
149                        ComplexPattern<i32, 2, "SelectT2AddrModeImm8s4", []> {
150  let PrintMethod = "printT2AddrModeImm8s4Operand";
151  let MIOperandInfo = (ops GPR:$base, i32imm:$offsimm);
152}
153
154def t2am_imm8s4_offset : Operand<i32> {
155  let PrintMethod = "printT2AddrModeImm8s4OffsetOperand";
156}
157
158// t2addrmode_so_reg  := reg + (reg << imm2)
159def t2addrmode_so_reg : Operand<i32>,
160                        ComplexPattern<i32, 3, "SelectT2AddrModeSoReg", []> {
161  let PrintMethod = "printT2AddrModeSoRegOperand";
162  let MIOperandInfo = (ops GPR:$base, rGPR:$offsreg, i32imm:$offsimm);
163}
164
165
166//===----------------------------------------------------------------------===//
167// Multiclass helpers...
168//
169
170/// T2I_un_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns for a
171/// unary operation that produces a value. These are predicable and can be
172/// changed to modify CPSR.
173multiclass T2I_un_irs<bits<4> opcod, string opc, PatFrag opnode,
174                      bit Cheap = 0, bit ReMat = 0> {
175   // shifted imm
176   def i : T2sI<(outs rGPR:$dst), (ins t2_so_imm:$src), IIC_iMOVi,
177                opc, "\t$dst, $src",
178                [(set rGPR:$dst, (opnode t2_so_imm:$src))]> {
179     let isAsCheapAsAMove = Cheap;
180     let isReMaterializable = ReMat;
181     let Inst{31-27} = 0b11110;
182     let Inst{25} = 0;
183     let Inst{24-21} = opcod;
184     let Inst{20} = ?; // The S bit.
185     let Inst{19-16} = 0b1111; // Rn
186     let Inst{15} = 0;
187   }
188   // register
189   def r : T2sI<(outs rGPR:$dst), (ins rGPR:$src), IIC_iMOVr,
190                opc, ".w\t$dst, $src",
191                [(set rGPR:$dst, (opnode rGPR:$src))]> {
192     let Inst{31-27} = 0b11101;
193     let Inst{26-25} = 0b01;
194     let Inst{24-21} = opcod;
195     let Inst{20} = ?; // The S bit.
196     let Inst{19-16} = 0b1111; // Rn
197     let Inst{14-12} = 0b000; // imm3
198     let Inst{7-6} = 0b00; // imm2
199     let Inst{5-4} = 0b00; // type
200   }
201   // shifted register
202   def s : T2sI<(outs rGPR:$dst), (ins t2_so_reg:$src), IIC_iMOVsi,
203                opc, ".w\t$dst, $src",
204                [(set rGPR:$dst, (opnode t2_so_reg:$src))]> {
205     let Inst{31-27} = 0b11101;
206     let Inst{26-25} = 0b01;
207     let Inst{24-21} = opcod;
208     let Inst{20} = ?; // The S bit.
209     let Inst{19-16} = 0b1111; // Rn
210   }
211}
212
213/// T2I_bin_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns for a
214/// binary operation that produces a value. These are predicable and can be
215/// changed to modify CPSR.
216multiclass T2I_bin_irs<bits<4> opcod, string opc, PatFrag opnode,
217                       bit Commutable = 0, string wide = ""> {
218   // shifted imm
219   def ri : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
220                 opc, "\t$dst, $lhs, $rhs",
221                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_imm:$rhs))]> {
222     let Inst{31-27} = 0b11110;
223     let Inst{25} = 0;
224     let Inst{24-21} = opcod;
225     let Inst{20} = ?; // The S bit.
226     let Inst{15} = 0;
227   }
228   // register
229   def rr : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, rGPR:$rhs), IIC_iALUr,
230                 opc, !strconcat(wide, "\t$dst, $lhs, $rhs"),
231                 [(set rGPR:$dst, (opnode rGPR:$lhs, rGPR:$rhs))]> {
232     let isCommutable = Commutable;
233     let Inst{31-27} = 0b11101;
234     let Inst{26-25} = 0b01;
235     let Inst{24-21} = opcod;
236     let Inst{20} = ?; // The S bit.
237     let Inst{14-12} = 0b000; // imm3
238     let Inst{7-6} = 0b00; // imm2
239     let Inst{5-4} = 0b00; // type
240   }
241   // shifted register
242   def rs : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
243                 opc, !strconcat(wide, "\t$dst, $lhs, $rhs"),
244                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_reg:$rhs))]> {
245     let Inst{31-27} = 0b11101;
246     let Inst{26-25} = 0b01;
247     let Inst{24-21} = opcod;
248     let Inst{20} = ?; // The S bit.
249   }
250}
251
252/// T2I_bin_w_irs - Same as T2I_bin_irs except these operations need
253//  the ".w" prefix to indicate that they are wide.
254multiclass T2I_bin_w_irs<bits<4> opcod, string opc, PatFrag opnode,
255                         bit Commutable = 0> :
256    T2I_bin_irs<opcod, opc, opnode, Commutable, ".w">;
257
258/// T2I_rbin_is - Same as T2I_bin_irs except the order of operands are
259/// reversed.  The 'rr' form is only defined for the disassembler; for codegen
260/// it is equivalent to the T2I_bin_irs counterpart.
261multiclass T2I_rbin_irs<bits<4> opcod, string opc, PatFrag opnode> {
262   // shifted imm
263   def ri : T2sI<(outs rGPR:$dst), (ins rGPR:$rhs, t2_so_imm:$lhs), IIC_iALUi,
264                 opc, ".w\t$dst, $rhs, $lhs",
265                 [(set rGPR:$dst, (opnode t2_so_imm:$lhs, rGPR:$rhs))]> {
266     let Inst{31-27} = 0b11110;
267     let Inst{25} = 0;
268     let Inst{24-21} = opcod;
269     let Inst{20} = ?; // The S bit.
270     let Inst{15} = 0;
271   }
272   // register
273   def rr : T2sI<(outs rGPR:$dst), (ins rGPR:$rhs, rGPR:$lhs), IIC_iALUr,
274                 opc, "\t$dst, $rhs, $lhs",
275                 [/* For disassembly only; pattern left blank */]> {
276     let Inst{31-27} = 0b11101;
277     let Inst{26-25} = 0b01;
278     let Inst{24-21} = opcod;
279     let Inst{20} = ?; // The S bit.
280     let Inst{14-12} = 0b000; // imm3
281     let Inst{7-6} = 0b00; // imm2
282     let Inst{5-4} = 0b00; // type
283   }
284   // shifted register
285   def rs : T2sI<(outs rGPR:$dst), (ins rGPR:$rhs, t2_so_reg:$lhs), IIC_iALUsi,
286                 opc, "\t$dst, $rhs, $lhs",
287                 [(set rGPR:$dst, (opnode t2_so_reg:$lhs, rGPR:$rhs))]> {
288     let Inst{31-27} = 0b11101;
289     let Inst{26-25} = 0b01;
290     let Inst{24-21} = opcod;
291     let Inst{20} = ?; // The S bit.
292   }
293}
294
295/// T2I_bin_s_irs - Similar to T2I_bin_irs except it sets the 's' bit so the
296/// instruction modifies the CPSR register.
297let Defs = [CPSR] in {
298multiclass T2I_bin_s_irs<bits<4> opcod, string opc, PatFrag opnode,
299                         bit Commutable = 0> {
300   // shifted imm
301   def ri : T2I<(outs rGPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
302                !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
303                [(set rGPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]> {
304     let Inst{31-27} = 0b11110;
305     let Inst{25} = 0;
306     let Inst{24-21} = opcod;
307     let Inst{20} = 1; // The S bit.
308     let Inst{15} = 0;
309   }
310   // register
311   def rr : T2I<(outs rGPR:$dst), (ins GPR:$lhs, rGPR:$rhs), IIC_iALUr,
312                !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
313                [(set rGPR:$dst, (opnode GPR:$lhs, rGPR:$rhs))]> {
314     let isCommutable = Commutable;
315     let Inst{31-27} = 0b11101;
316     let Inst{26-25} = 0b01;
317     let Inst{24-21} = opcod;
318     let Inst{20} = 1; // The S bit.
319     let Inst{14-12} = 0b000; // imm3
320     let Inst{7-6} = 0b00; // imm2
321     let Inst{5-4} = 0b00; // type
322   }
323   // shifted register
324   def rs : T2I<(outs rGPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
325                !strconcat(opc, "s"), ".w\t$dst, $lhs, $rhs",
326                [(set rGPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]> {
327     let Inst{31-27} = 0b11101;
328     let Inst{26-25} = 0b01;
329     let Inst{24-21} = opcod;
330     let Inst{20} = 1; // The S bit.
331   }
332}
333}
334
335/// T2I_bin_ii12rs - Defines a set of (op reg, {so_imm|imm0_4095|r|so_reg})
336/// patterns for a binary operation that produces a value.
337multiclass T2I_bin_ii12rs<bits<3> op23_21, string opc, PatFrag opnode,
338                          bit Commutable = 0> {
339   // shifted imm
340   // The register-immediate version is re-materializable. This is useful
341   // in particular for taking the address of a local.
342   let isReMaterializable = 1 in {
343   def ri : T2sI<(outs rGPR:$dst), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
344                 opc, ".w\t$dst, $lhs, $rhs",
345                 [(set rGPR:$dst, (opnode GPR:$lhs, t2_so_imm:$rhs))]> {
346     let Inst{31-27} = 0b11110;
347     let Inst{25} = 0;
348     let Inst{24} = 1;
349     let Inst{23-21} = op23_21;
350     let Inst{20} = 0; // The S bit.
351     let Inst{15} = 0;
352   }
353   }
354   // 12-bit imm
355   def ri12 : T2I<(outs rGPR:$dst), (ins GPR:$lhs, imm0_4095:$rhs), IIC_iALUi,
356                  !strconcat(opc, "w"), "\t$dst, $lhs, $rhs",
357                  [(set rGPR:$dst, (opnode GPR:$lhs, imm0_4095:$rhs))]> {
358     let Inst{31-27} = 0b11110;
359     let Inst{25} = 1;
360     let Inst{24} = 0;
361     let Inst{23-21} = op23_21;
362     let Inst{20} = 0; // The S bit.
363     let Inst{15} = 0;
364   }
365   // register
366   def rr : T2sI<(outs rGPR:$dst), (ins GPR:$lhs, rGPR:$rhs), IIC_iALUr,
367                 opc, ".w\t$dst, $lhs, $rhs",
368                 [(set rGPR:$dst, (opnode GPR:$lhs, rGPR:$rhs))]> {
369     let isCommutable = Commutable;
370     let Inst{31-27} = 0b11101;
371     let Inst{26-25} = 0b01;
372     let Inst{24} = 1;
373     let Inst{23-21} = op23_21;
374     let Inst{20} = 0; // The S bit.
375     let Inst{14-12} = 0b000; // imm3
376     let Inst{7-6} = 0b00; // imm2
377     let Inst{5-4} = 0b00; // type
378   }
379   // shifted register
380   def rs : T2sI<(outs rGPR:$dst), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
381                 opc, ".w\t$dst, $lhs, $rhs",
382                 [(set rGPR:$dst, (opnode GPR:$lhs, t2_so_reg:$rhs))]> {
383     let Inst{31-27} = 0b11101;
384     let Inst{26-25} = 0b01;
385     let Inst{24} = 1;
386     let Inst{23-21} = op23_21;
387     let Inst{20} = 0; // The S bit.
388   }
389}
390
391/// T2I_adde_sube_irs - Defines a set of (op reg, {so_imm|r|so_reg}) patterns
392/// for a binary operation that produces a value and use the carry
393/// bit. It's not predicable.
394let Uses = [CPSR] in {
395multiclass T2I_adde_sube_irs<bits<4> opcod, string opc, PatFrag opnode,
396                             bit Commutable = 0> {
397   // shifted imm
398   def ri : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
399                 opc, "\t$dst, $lhs, $rhs",
400                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_imm:$rhs))]>,
401                 Requires<[IsThumb2]> {
402     let Inst{31-27} = 0b11110;
403     let Inst{25} = 0;
404     let Inst{24-21} = opcod;
405     let Inst{20} = 0; // The S bit.
406     let Inst{15} = 0;
407   }
408   // register
409   def rr : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, rGPR:$rhs), IIC_iALUr,
410                 opc, ".w\t$dst, $lhs, $rhs",
411                 [(set rGPR:$dst, (opnode rGPR:$lhs, rGPR:$rhs))]>,
412                 Requires<[IsThumb2]> {
413     let isCommutable = Commutable;
414     let Inst{31-27} = 0b11101;
415     let Inst{26-25} = 0b01;
416     let Inst{24-21} = opcod;
417     let Inst{20} = 0; // The S bit.
418     let Inst{14-12} = 0b000; // imm3
419     let Inst{7-6} = 0b00; // imm2
420     let Inst{5-4} = 0b00; // type
421   }
422   // shifted register
423   def rs : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
424                 opc, ".w\t$dst, $lhs, $rhs",
425                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_reg:$rhs))]>,
426                 Requires<[IsThumb2]> {
427     let Inst{31-27} = 0b11101;
428     let Inst{26-25} = 0b01;
429     let Inst{24-21} = opcod;
430     let Inst{20} = 0; // The S bit.
431   }
432}
433
434// Carry setting variants
435let Defs = [CPSR] in {
436multiclass T2I_adde_sube_s_irs<bits<4> opcod, string opc, PatFrag opnode,
437                               bit Commutable = 0> {
438   // shifted imm
439   def ri : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_imm:$rhs), IIC_iALUi,
440                 opc, "\t$dst, $lhs, $rhs",
441                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_imm:$rhs))]>,
442                 Requires<[IsThumb2]> {
443     let Inst{31-27} = 0b11110;
444     let Inst{25} = 0;
445     let Inst{24-21} = opcod;
446     let Inst{20} = 1; // The S bit.
447     let Inst{15} = 0;
448   }
449   // register
450   def rr : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, rGPR:$rhs), IIC_iALUr,
451                 opc, ".w\t$dst, $lhs, $rhs",
452                 [(set rGPR:$dst, (opnode rGPR:$lhs, rGPR:$rhs))]>,
453                 Requires<[IsThumb2]> {
454     let isCommutable = Commutable;
455     let Inst{31-27} = 0b11101;
456     let Inst{26-25} = 0b01;
457     let Inst{24-21} = opcod;
458     let Inst{20} = 1; // The S bit.
459     let Inst{14-12} = 0b000; // imm3
460     let Inst{7-6} = 0b00; // imm2
461     let Inst{5-4} = 0b00; // type
462   }
463   // shifted register
464   def rs : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, t2_so_reg:$rhs), IIC_iALUsi,
465                 opc, ".w\t$dst, $lhs, $rhs",
466                 [(set rGPR:$dst, (opnode rGPR:$lhs, t2_so_reg:$rhs))]>,
467                 Requires<[IsThumb2]> {
468     let Inst{31-27} = 0b11101;
469     let Inst{26-25} = 0b01;
470     let Inst{24-21} = opcod;
471     let Inst{20} = 1; // The S bit.
472   }
473}
474}
475}
476
477/// T2I_rbin_s_is - Same as T2I_rbin_irs except sets 's' bit and the register
478/// version is not needed since this is only for codegen.
479let Defs = [CPSR] in {
480multiclass T2I_rbin_s_is<bits<4> opcod, string opc, PatFrag opnode> {
481   // shifted imm
482   def ri : T2I<(outs rGPR:$dst), (ins rGPR:$rhs, t2_so_imm:$lhs), IIC_iALUi,
483                !strconcat(opc, "s"), ".w\t$dst, $rhs, $lhs",
484                [(set rGPR:$dst, (opnode t2_so_imm:$lhs, rGPR:$rhs))]> {
485     let Inst{31-27} = 0b11110;
486     let Inst{25} = 0;
487     let Inst{24-21} = opcod;
488     let Inst{20} = 1; // The S bit.
489     let Inst{15} = 0;
490   }
491   // shifted register
492   def rs : T2I<(outs rGPR:$dst), (ins rGPR:$rhs, t2_so_reg:$lhs), IIC_iALUsi,
493                !strconcat(opc, "s"), "\t$dst, $rhs, $lhs",
494                [(set rGPR:$dst, (opnode t2_so_reg:$lhs, rGPR:$rhs))]> {
495     let Inst{31-27} = 0b11101;
496     let Inst{26-25} = 0b01;
497     let Inst{24-21} = opcod;
498     let Inst{20} = 1; // The S bit.
499   }
500}
501}
502
503/// T2I_sh_ir - Defines a set of (op reg, {so_imm|r}) patterns for a shift /
504//  rotate operation that produces a value.
505multiclass T2I_sh_ir<bits<2> opcod, string opc, PatFrag opnode> {
506   // 5-bit imm
507   def ri : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, i32imm:$rhs), IIC_iMOVsi,
508                 opc, ".w\t$dst, $lhs, $rhs",
509                 [(set rGPR:$dst, (opnode rGPR:$lhs, imm1_31:$rhs))]> {
510     let Inst{31-27} = 0b11101;
511     let Inst{26-21} = 0b010010;
512     let Inst{19-16} = 0b1111; // Rn
513     let Inst{5-4} = opcod;
514   }
515   // register
516   def rr : T2sI<(outs rGPR:$dst), (ins rGPR:$lhs, rGPR:$rhs), IIC_iMOVsr,
517                 opc, ".w\t$dst, $lhs, $rhs",
518                 [(set rGPR:$dst, (opnode rGPR:$lhs, rGPR:$rhs))]> {
519     let Inst{31-27} = 0b11111;
520     let Inst{26-23} = 0b0100;
521     let Inst{22-21} = opcod;
522     let Inst{15-12} = 0b1111;
523     let Inst{7-4} = 0b0000;
524   }
525}
526
527/// T2I_cmp_irs - Defines a set of (op r, {so_imm|r|so_reg}) cmp / test
528/// patterns. Similar to T2I_bin_irs except the instruction does not produce
529/// a explicit result, only implicitly set CPSR.
530let isCompare = 1, Defs = [CPSR] in {
531multiclass T2I_cmp_irs<bits<4> opcod, string opc, PatFrag opnode> {
532   // shifted imm
533   def ri : T2I<(outs), (ins GPR:$lhs, t2_so_imm:$rhs), IIC_iCMPi,
534                opc, ".w\t$lhs, $rhs",
535                [(opnode GPR:$lhs, t2_so_imm:$rhs)]> {
536     let Inst{31-27} = 0b11110;
537     let Inst{25} = 0;
538     let Inst{24-21} = opcod;
539     let Inst{20} = 1; // The S bit.
540     let Inst{15} = 0;
541     let Inst{11-8} = 0b1111; // Rd
542   }
543   // register
544   def rr : T2I<(outs), (ins GPR:$lhs, rGPR:$rhs), IIC_iCMPr,
545                opc, ".w\t$lhs, $rhs",
546                [(opnode GPR:$lhs, rGPR:$rhs)]> {
547     let Inst{31-27} = 0b11101;
548     let Inst{26-25} = 0b01;
549     let Inst{24-21} = opcod;
550     let Inst{20} = 1; // The S bit.
551     let Inst{14-12} = 0b000; // imm3
552     let Inst{11-8} = 0b1111; // Rd
553     let Inst{7-6} = 0b00; // imm2
554     let Inst{5-4} = 0b00; // type
555   }
556   // shifted register
557   def rs : T2I<(outs), (ins GPR:$lhs, t2_so_reg:$rhs), IIC_iCMPsi,
558                opc, ".w\t$lhs, $rhs",
559                [(opnode GPR:$lhs, t2_so_reg:$rhs)]> {
560     let Inst{31-27} = 0b11101;
561     let Inst{26-25} = 0b01;
562     let Inst{24-21} = opcod;
563     let Inst{20} = 1; // The S bit.
564     let Inst{11-8} = 0b1111; // Rd
565   }
566}
567}
568
569/// T2I_ld - Defines a set of (op r, {imm12|imm8|so_reg}) load patterns.
570multiclass T2I_ld<bit signed, bits<2> opcod, string opc, PatFrag opnode> {
571  def i12 : T2Ii12<(outs GPR:$dst), (ins t2addrmode_imm12:$addr), IIC_iLoadi,
572                   opc, ".w\t$dst, $addr",
573                   [(set GPR:$dst, (opnode t2addrmode_imm12:$addr))]> {
574    let Inst{31-27} = 0b11111;
575    let Inst{26-25} = 0b00;
576    let Inst{24} = signed;
577    let Inst{23} = 1;
578    let Inst{22-21} = opcod;
579    let Inst{20} = 1; // load
580  }
581  def i8  : T2Ii8 <(outs GPR:$dst), (ins t2addrmode_imm8:$addr), IIC_iLoadi,
582                   opc, "\t$dst, $addr",
583                   [(set GPR:$dst, (opnode t2addrmode_imm8:$addr))]> {
584    let Inst{31-27} = 0b11111;
585    let Inst{26-25} = 0b00;
586    let Inst{24} = signed;
587    let Inst{23} = 0;
588    let Inst{22-21} = opcod;
589    let Inst{20} = 1; // load
590    let Inst{11} = 1;
591    // Offset: index==TRUE, wback==FALSE
592    let Inst{10} = 1; // The P bit.
593    let Inst{8} = 0; // The W bit.
594  }
595  def s   : T2Iso <(outs GPR:$dst), (ins t2addrmode_so_reg:$addr), IIC_iLoadr,
596                   opc, ".w\t$dst, $addr",
597                   [(set GPR:$dst, (opnode t2addrmode_so_reg:$addr))]> {
598    let Inst{31-27} = 0b11111;
599    let Inst{26-25} = 0b00;
600    let Inst{24} = signed;
601    let Inst{23} = 0;
602    let Inst{22-21} = opcod;
603    let Inst{20} = 1; // load
604    let Inst{11-6} = 0b000000;
605  }
606  def pci : T2Ipc <(outs GPR:$dst), (ins i32imm:$addr), IIC_iLoadi,
607                   opc, ".w\t$dst, $addr",
608                   [(set GPR:$dst, (opnode (ARMWrapper tconstpool:$addr)))]> {
609    let isReMaterializable = 1;
610    let Inst{31-27} = 0b11111;
611    let Inst{26-25} = 0b00;
612    let Inst{24} = signed;
613    let Inst{23} = ?; // add = (U == '1')
614    let Inst{22-21} = opcod;
615    let Inst{20} = 1; // load
616    let Inst{19-16} = 0b1111; // Rn
617  }
618}
619
620/// T2I_st - Defines a set of (op r, {imm12|imm8|so_reg}) store patterns.
621multiclass T2I_st<bits<2> opcod, string opc, PatFrag opnode> {
622  def i12 : T2Ii12<(outs), (ins GPR:$src, t2addrmode_imm12:$addr), IIC_iStorei,
623                   opc, ".w\t$src, $addr",
624                   [(opnode GPR:$src, t2addrmode_imm12:$addr)]> {
625    let Inst{31-27} = 0b11111;
626    let Inst{26-23} = 0b0001;
627    let Inst{22-21} = opcod;
628    let Inst{20} = 0; // !load
629  }
630  def i8  : T2Ii8 <(outs), (ins GPR:$src, t2addrmode_imm8:$addr), IIC_iStorei,
631                   opc, "\t$src, $addr",
632                   [(opnode GPR:$src, t2addrmode_imm8:$addr)]> {
633    let Inst{31-27} = 0b11111;
634    let Inst{26-23} = 0b0000;
635    let Inst{22-21} = opcod;
636    let Inst{20} = 0; // !load
637    let Inst{11} = 1;
638    // Offset: index==TRUE, wback==FALSE
639    let Inst{10} = 1; // The P bit.
640    let Inst{8} = 0; // The W bit.
641  }
642  def s   : T2Iso <(outs), (ins GPR:$src, t2addrmode_so_reg:$addr), IIC_iStorer,
643                   opc, ".w\t$src, $addr",
644                   [(opnode GPR:$src, t2addrmode_so_reg:$addr)]> {
645    let Inst{31-27} = 0b11111;
646    let Inst{26-23} = 0b0000;
647    let Inst{22-21} = opcod;
648    let Inst{20} = 0; // !load
649    let Inst{11-6} = 0b000000;
650  }
651}
652
653/// T2I_unary_rrot - A unary operation with two forms: one whose operand is a
654/// register and one whose operand is a register rotated by 8/16/24.
655multiclass T2I_unary_rrot<bits<3> opcod, string opc, PatFrag opnode> {
656  def r     : T2I<(outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
657                  opc, ".w\t$dst, $src",
658                 [(set rGPR:$dst, (opnode rGPR:$src))]> {
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} = 0b00; // rotate
666   }
667  def r_rot : T2I<(outs rGPR:$dst), (ins rGPR:$src, i32imm:$rot), IIC_iUNAsi,
668                  opc, ".w\t$dst, $src, ror $rot",
669                 [(set rGPR:$dst, (opnode (rotr rGPR:$src, rot_imm:$rot)))]> {
670     let Inst{31-27} = 0b11111;
671     let Inst{26-23} = 0b0100;
672     let Inst{22-20} = opcod;
673     let Inst{19-16} = 0b1111; // Rn
674     let Inst{15-12} = 0b1111;
675     let Inst{7} = 1;
676     let Inst{5-4} = {?,?}; // rotate
677   }
678}
679
680// UXTB16 - Requres T2ExtractPack, does not need the .w qualifier.
681multiclass T2I_unary_rrot_uxtb16<bits<3> opcod, string opc, PatFrag opnode> {
682  def r     : T2I<(outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
683                  opc, "\t$dst, $src",
684                 [(set rGPR:$dst, (opnode rGPR:$src))]>,
685                 Requires<[HasT2ExtractPack]> {
686     let Inst{31-27} = 0b11111;
687     let Inst{26-23} = 0b0100;
688     let Inst{22-20} = opcod;
689     let Inst{19-16} = 0b1111; // Rn
690     let Inst{15-12} = 0b1111;
691     let Inst{7} = 1;
692     let Inst{5-4} = 0b00; // rotate
693   }
694  def r_rot : T2I<(outs rGPR:$dst), (ins rGPR:$src, i32imm:$rot), IIC_iUNAsi,
695                  opc, "\t$dst, $src, ror $rot",
696                 [(set rGPR:$dst, (opnode (rotr rGPR:$src, rot_imm:$rot)))]>,
697                 Requires<[HasT2ExtractPack]> {
698     let Inst{31-27} = 0b11111;
699     let Inst{26-23} = 0b0100;
700     let Inst{22-20} = opcod;
701     let Inst{19-16} = 0b1111; // Rn
702     let Inst{15-12} = 0b1111;
703     let Inst{7} = 1;
704     let Inst{5-4} = {?,?}; // rotate
705   }
706}
707
708// SXTB16 - Requres T2ExtractPack, does not need the .w qualifier, no pattern
709// supported yet.
710multiclass T2I_unary_rrot_sxtb16<bits<3> opcod, string opc> {
711  def r     : T2I<(outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
712                  opc, "\t$dst, $src", []> {
713     let Inst{31-27} = 0b11111;
714     let Inst{26-23} = 0b0100;
715     let Inst{22-20} = opcod;
716     let Inst{19-16} = 0b1111; // Rn
717     let Inst{15-12} = 0b1111;
718     let Inst{7} = 1;
719     let Inst{5-4} = 0b00; // rotate
720   }
721  def r_rot : T2I<(outs rGPR:$dst), (ins rGPR:$src, i32imm:$rot), IIC_iUNAsi,
722                  opc, "\t$dst, $src, ror $rot", []> {
723     let Inst{31-27} = 0b11111;
724     let Inst{26-23} = 0b0100;
725     let Inst{22-20} = opcod;
726     let Inst{19-16} = 0b1111; // Rn
727     let Inst{15-12} = 0b1111;
728     let Inst{7} = 1;
729     let Inst{5-4} = {?,?}; // rotate
730   }
731}
732
733/// T2I_bin_rrot - A binary operation with two forms: one whose operand is a
734/// register and one whose operand is a register rotated by 8/16/24.
735multiclass T2I_bin_rrot<bits<3> opcod, string opc, PatFrag opnode> {
736  def rr     : T2I<(outs rGPR:$dst), (ins rGPR:$LHS, rGPR:$RHS), IIC_iALUr,
737                  opc, "\t$dst, $LHS, $RHS",
738                  [(set rGPR:$dst, (opnode rGPR:$LHS, rGPR:$RHS))]>,
739                  Requires<[HasT2ExtractPack]> {
740     let Inst{31-27} = 0b11111;
741     let Inst{26-23} = 0b0100;
742     let Inst{22-20} = opcod;
743     let Inst{15-12} = 0b1111;
744     let Inst{7} = 1;
745     let Inst{5-4} = 0b00; // rotate
746   }
747  def rr_rot : T2I<(outs rGPR:$dst), (ins rGPR:$LHS, rGPR:$RHS, i32imm:$rot),
748                  IIC_iALUsr, opc, "\t$dst, $LHS, $RHS, ror $rot",
749                  [(set rGPR:$dst, (opnode rGPR:$LHS,
750                                          (rotr rGPR:$RHS, rot_imm:$rot)))]>,
751                  Requires<[HasT2ExtractPack]> {
752     let Inst{31-27} = 0b11111;
753     let Inst{26-23} = 0b0100;
754     let Inst{22-20} = opcod;
755     let Inst{15-12} = 0b1111;
756     let Inst{7} = 1;
757     let Inst{5-4} = {?,?}; // rotate
758   }
759}
760
761// DO variant - disassembly only, no pattern
762
763multiclass T2I_bin_rrot_DO<bits<3> opcod, string opc> {
764  def rr     : T2I<(outs rGPR:$dst), (ins rGPR:$LHS, rGPR:$RHS), IIC_iALUr,
765                  opc, "\t$dst, $LHS, $RHS", []> {
766     let Inst{31-27} = 0b11111;
767     let Inst{26-23} = 0b0100;
768     let Inst{22-20} = opcod;
769     let Inst{15-12} = 0b1111;
770     let Inst{7} = 1;
771     let Inst{5-4} = 0b00; // rotate
772   }
773  def rr_rot : T2I<(outs rGPR:$dst), (ins rGPR:$LHS, rGPR:$RHS, i32imm:$rot),
774                  IIC_iALUsr, opc, "\t$dst, $LHS, $RHS, ror $rot", []> {
775     let Inst{31-27} = 0b11111;
776     let Inst{26-23} = 0b0100;
777     let Inst{22-20} = opcod;
778     let Inst{15-12} = 0b1111;
779     let Inst{7} = 1;
780     let Inst{5-4} = {?,?}; // rotate
781   }
782}
783
784//===----------------------------------------------------------------------===//
785// Instructions
786//===----------------------------------------------------------------------===//
787
788//===----------------------------------------------------------------------===//
789//  Miscellaneous Instructions.
790//
791
792// LEApcrel - Load a pc-relative address into a register without offending the
793// assembler.
794let neverHasSideEffects = 1 in {
795let isReMaterializable = 1 in
796def t2LEApcrel : T2XI<(outs rGPR:$dst), (ins i32imm:$label, pred:$p), IIC_iALUi,
797                      "adr${p}.w\t$dst, #$label", []> {
798  let Inst{31-27} = 0b11110;
799  let Inst{25-24} = 0b10;
800  // Inst{23:21} = '11' (add = FALSE) or '00' (add = TRUE)
801  let Inst{22} = 0;
802  let Inst{20} = 0;
803  let Inst{19-16} = 0b1111; // Rn
804  let Inst{15} = 0;
805}
806} // neverHasSideEffects
807def t2LEApcrelJT : T2XI<(outs rGPR:$dst),
808                        (ins i32imm:$label, nohash_imm:$id, pred:$p), IIC_iALUi,
809                        "adr${p}.w\t$dst, #${label}_${id}", []> {
810  let Inst{31-27} = 0b11110;
811  let Inst{25-24} = 0b10;
812  // Inst{23:21} = '11' (add = FALSE) or '00' (add = TRUE)
813  let Inst{22} = 0;
814  let Inst{20} = 0;
815  let Inst{19-16} = 0b1111; // Rn
816  let Inst{15} = 0;
817}
818
819// ADD r, sp, {so_imm|i12}
820def t2ADDrSPi   : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_imm:$imm),
821                        IIC_iALUi, "add", ".w\t$dst, $sp, $imm", []> {
822  let Inst{31-27} = 0b11110;
823  let Inst{25} = 0;
824  let Inst{24-21} = 0b1000;
825  let Inst{20} = ?; // The S bit.
826  let Inst{19-16} = 0b1101; // Rn = sp
827  let Inst{15} = 0;
828}
829def t2ADDrSPi12 : T2I<(outs GPR:$dst), (ins GPR:$sp, imm0_4095:$imm),
830                       IIC_iALUi, "addw", "\t$dst, $sp, $imm", []> {
831  let Inst{31-27} = 0b11110;
832  let Inst{25} = 1;
833  let Inst{24-21} = 0b0000;
834  let Inst{20} = 0; // The S bit.
835  let Inst{19-16} = 0b1101; // Rn = sp
836  let Inst{15} = 0;
837}
838
839// ADD r, sp, so_reg
840def t2ADDrSPs   : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_reg:$rhs),
841                        IIC_iALUsi, "add", ".w\t$dst, $sp, $rhs", []> {
842  let Inst{31-27} = 0b11101;
843  let Inst{26-25} = 0b01;
844  let Inst{24-21} = 0b1000;
845  let Inst{20} = ?; // The S bit.
846  let Inst{19-16} = 0b1101; // Rn = sp
847  let Inst{15} = 0;
848}
849
850// SUB r, sp, {so_imm|i12}
851def t2SUBrSPi   : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_imm:$imm),
852                        IIC_iALUi, "sub", ".w\t$dst, $sp, $imm", []> {
853  let Inst{31-27} = 0b11110;
854  let Inst{25} = 0;
855  let Inst{24-21} = 0b1101;
856  let Inst{20} = ?; // The S bit.
857  let Inst{19-16} = 0b1101; // Rn = sp
858  let Inst{15} = 0;
859}
860def t2SUBrSPi12 : T2I<(outs GPR:$dst), (ins GPR:$sp, imm0_4095:$imm),
861                       IIC_iALUi, "subw", "\t$dst, $sp, $imm", []> {
862  let Inst{31-27} = 0b11110;
863  let Inst{25} = 1;
864  let Inst{24-21} = 0b0101;
865  let Inst{20} = 0; // The S bit.
866  let Inst{19-16} = 0b1101; // Rn = sp
867  let Inst{15} = 0;
868}
869
870// SUB r, sp, so_reg
871def t2SUBrSPs   : T2sI<(outs GPR:$dst), (ins GPR:$sp, t2_so_reg:$rhs),
872                       IIC_iALUsi,
873                       "sub", "\t$dst, $sp, $rhs", []> {
874  let Inst{31-27} = 0b11101;
875  let Inst{26-25} = 0b01;
876  let Inst{24-21} = 0b1101;
877  let Inst{20} = ?; // The S bit.
878  let Inst{19-16} = 0b1101; // Rn = sp
879  let Inst{15} = 0;
880}
881
882// Signed and unsigned division on v7-M
883def t2SDIV : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iALUi, 
884                 "sdiv", "\t$dst, $a, $b",
885                 [(set rGPR:$dst, (sdiv rGPR:$a, rGPR:$b))]>,
886                 Requires<[HasDivide]> {
887  let Inst{31-27} = 0b11111;
888  let Inst{26-21} = 0b011100;
889  let Inst{20} = 0b1;
890  let Inst{15-12} = 0b1111;
891  let Inst{7-4} = 0b1111;
892}
893
894def t2UDIV : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iALUi, 
895                 "udiv", "\t$dst, $a, $b",
896                 [(set rGPR:$dst, (udiv rGPR:$a, rGPR:$b))]>,
897                 Requires<[HasDivide]> {
898  let Inst{31-27} = 0b11111;
899  let Inst{26-21} = 0b011101;
900  let Inst{20} = 0b1;
901  let Inst{15-12} = 0b1111;
902  let Inst{7-4} = 0b1111;
903}
904
905//===----------------------------------------------------------------------===//
906//  Load / store Instructions.
907//
908
909// Load
910let canFoldAsLoad = 1, isReMaterializable = 1  in
911defm t2LDR   : T2I_ld<0, 0b10, "ldr",  UnOpFrag<(load node:$Src)>>;
912
913// Loads with zero extension
914defm t2LDRH  : T2I_ld<0, 0b01, "ldrh", UnOpFrag<(zextloadi16 node:$Src)>>;
915defm t2LDRB  : T2I_ld<0, 0b00, "ldrb", UnOpFrag<(zextloadi8  node:$Src)>>;
916
917// Loads with sign extension
918defm t2LDRSH : T2I_ld<1, 0b01, "ldrsh", UnOpFrag<(sextloadi16 node:$Src)>>;
919defm t2LDRSB : T2I_ld<1, 0b00, "ldrsb", UnOpFrag<(sextloadi8  node:$Src)>>;
920
921let mayLoad = 1, neverHasSideEffects = 1, hasExtraDefRegAllocReq = 1 in {
922// Load doubleword
923def t2LDRDi8  : T2Ii8s4<1, 0, 1, (outs rGPR:$dst1, rGPR:$dst2),
924                        (ins t2addrmode_imm8s4:$addr),
925                        IIC_iLoadi, "ldrd", "\t$dst1, $addr", []>;
926def t2LDRDpci : T2Ii8s4<1, 0, 1, (outs rGPR:$dst1, rGPR:$dst2),
927                        (ins i32imm:$addr), IIC_iLoadi,
928                       "ldrd", "\t$dst1, $addr", []> {
929  let Inst{19-16} = 0b1111; // Rn
930}
931} // mayLoad = 1, neverHasSideEffects = 1, hasExtraDefRegAllocReq = 1
932
933// zextload i1 -> zextload i8
934def : T2Pat<(zextloadi1 t2addrmode_imm12:$addr),
935            (t2LDRBi12  t2addrmode_imm12:$addr)>;
936def : T2Pat<(zextloadi1 t2addrmode_imm8:$addr),
937            (t2LDRBi8   t2addrmode_imm8:$addr)>;
938def : T2Pat<(zextloadi1 t2addrmode_so_reg:$addr),
939            (t2LDRBs    t2addrmode_so_reg:$addr)>;
940def : T2Pat<(zextloadi1 (ARMWrapper tconstpool:$addr)),
941            (t2LDRBpci  tconstpool:$addr)>;
942
943// extload -> zextload
944// FIXME: Reduce the number of patterns by legalizing extload to zextload
945// earlier?
946def : T2Pat<(extloadi1  t2addrmode_imm12:$addr),
947            (t2LDRBi12  t2addrmode_imm12:$addr)>;
948def : T2Pat<(extloadi1  t2addrmode_imm8:$addr),
949            (t2LDRBi8   t2addrmode_imm8:$addr)>;
950def : T2Pat<(extloadi1  t2addrmode_so_reg:$addr),
951            (t2LDRBs    t2addrmode_so_reg:$addr)>;
952def : T2Pat<(extloadi1  (ARMWrapper tconstpool:$addr)),
953            (t2LDRBpci  tconstpool:$addr)>;
954
955def : T2Pat<(extloadi8  t2addrmode_imm12:$addr),
956            (t2LDRBi12  t2addrmode_imm12:$addr)>;
957def : T2Pat<(extloadi8  t2addrmode_imm8:$addr),
958            (t2LDRBi8   t2addrmode_imm8:$addr)>;
959def : T2Pat<(extloadi8  t2addrmode_so_reg:$addr),
960            (t2LDRBs    t2addrmode_so_reg:$addr)>;
961def : T2Pat<(extloadi8  (ARMWrapper tconstpool:$addr)),
962            (t2LDRBpci  tconstpool:$addr)>;
963
964def : T2Pat<(extloadi16 t2addrmode_imm12:$addr),
965            (t2LDRHi12  t2addrmode_imm12:$addr)>;
966def : T2Pat<(extloadi16 t2addrmode_imm8:$addr),
967            (t2LDRHi8   t2addrmode_imm8:$addr)>;
968def : T2Pat<(extloadi16 t2addrmode_so_reg:$addr),
969            (t2LDRHs    t2addrmode_so_reg:$addr)>;
970def : T2Pat<(extloadi16 (ARMWrapper tconstpool:$addr)),
971            (t2LDRHpci  tconstpool:$addr)>;
972
973// FIXME: The destination register of the loads and stores can't be PC, but
974//        can be SP. We need another regclass (similar to rGPR) to represent
975//        that. Not a pressing issue since these are selected manually,
976//        not via pattern.
977
978// Indexed loads
979let mayLoad = 1, neverHasSideEffects = 1 in {
980def t2LDR_PRE  : T2Iidxldst<0, 0b10, 1, 1, (outs GPR:$dst, GPR:$base_wb),
981                            (ins t2addrmode_imm8:$addr),
982                            AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
983                            "ldr", "\t$dst, $addr!", "$addr.base = $base_wb",
984                            []>;
985
986def t2LDR_POST : T2Iidxldst<0, 0b10, 1, 0, (outs GPR:$dst, GPR:$base_wb),
987                            (ins GPR:$base, t2am_imm8_offset:$offset),
988                            AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
989                          "ldr", "\t$dst, [$base], $offset", "$base = $base_wb",
990                            []>;
991
992def t2LDRB_PRE : T2Iidxldst<0, 0b00, 1, 1, (outs GPR:$dst, GPR:$base_wb),
993                            (ins t2addrmode_imm8:$addr),
994                            AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
995                            "ldrb", "\t$dst, $addr!", "$addr.base = $base_wb",
996                            []>;
997def t2LDRB_POST : T2Iidxldst<0, 0b00, 1, 0, (outs GPR:$dst, GPR:$base_wb),
998                            (ins GPR:$base, t2am_imm8_offset:$offset),
999                            AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
1000                         "ldrb", "\t$dst, [$base], $offset", "$base = $base_wb",
1001                            []>;
1002
1003def t2LDRH_PRE : T2Iidxldst<0, 0b01, 1, 1, (outs GPR:$dst, GPR:$base_wb),
1004                            (ins t2addrmode_imm8:$addr),
1005                            AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
1006                            "ldrh", "\t$dst, $addr!", "$addr.base = $base_wb",
1007                            []>;
1008def t2LDRH_POST : T2Iidxldst<0, 0b01, 1, 0, (outs GPR:$dst, GPR:$base_wb),
1009                            (ins GPR:$base, t2am_imm8_offset:$offset),
1010                            AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
1011                         "ldrh", "\t$dst, [$base], $offset", "$base = $base_wb",
1012                            []>;
1013
1014def t2LDRSB_PRE : T2Iidxldst<1, 0b00, 1, 1, (outs GPR:$dst, GPR:$base_wb),
1015                            (ins t2addrmode_imm8:$addr),
1016                            AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
1017                            "ldrsb", "\t$dst, $addr!", "$addr.base = $base_wb",
1018                            []>;
1019def t2LDRSB_POST : T2Iidxldst<1, 0b00, 1, 0, (outs GPR:$dst, GPR:$base_wb),
1020                            (ins GPR:$base, t2am_imm8_offset:$offset),
1021                            AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
1022                        "ldrsb", "\t$dst, [$base], $offset", "$base = $base_wb",
1023                            []>;
1024
1025def t2LDRSH_PRE : T2Iidxldst<1, 0b01, 1, 1, (outs GPR:$dst, GPR:$base_wb),
1026                            (ins t2addrmode_imm8:$addr),
1027                            AddrModeT2_i8, IndexModePre, IIC_iLoadiu,
1028                            "ldrsh", "\t$dst, $addr!", "$addr.base = $base_wb",
1029                            []>;
1030def t2LDRSH_POST : T2Iidxldst<1, 0b01, 1, 0, (outs GPR:$dst, GPR:$base_wb),
1031                            (ins GPR:$base, t2am_imm8_offset:$offset),
1032                            AddrModeT2_i8, IndexModePost, IIC_iLoadiu,
1033                        "ldrsh", "\t$dst, [$base], $offset", "$base = $base_wb",
1034                            []>;
1035} // mayLoad = 1, neverHasSideEffects = 1 
1036
1037// LDRT, LDRBT, LDRHT, LDRSBT, LDRSHT all have offset mode (PUW=0b110) and are
1038// for disassembly only.
1039// Ref: A8.6.57 LDR (immediate, Thumb) Encoding T4
1040class T2IldT<bit signed, bits<2> type, string opc>
1041  : T2Ii8<(outs GPR:$dst), (ins t2addrmode_imm8:$addr), IIC_iLoadi, opc,
1042          "\t$dst, $addr", []> {
1043  let Inst{31-27} = 0b11111;
1044  let Inst{26-25} = 0b00;
1045  let Inst{24} = signed;
1046  let Inst{23} = 0;
1047  let Inst{22-21} = type;
1048  let Inst{20} = 1; // load
1049  let Inst{11} = 1;
1050  let Inst{10-8} = 0b110; // PUW.
1051}
1052
1053def t2LDRT   : T2IldT<0, 0b10, "ldrt">;
1054def t2LDRBT  : T2IldT<0, 0b00, "ldrbt">;
1055def t2LDRHT  : T2IldT<0, 0b01, "ldrht">;
1056def t2LDRSBT : T2IldT<1, 0b00, "ldrsbt">;
1057def t2LDRSHT : T2IldT<1, 0b01, "ldrsht">;
1058
1059// Store
1060defm t2STR :T2I_st<0b10,"str", BinOpFrag<(store node:$LHS, node:$RHS)>>;
1061defm t2STRB:T2I_st<0b00,"strb",BinOpFrag<(truncstorei8 node:$LHS, node:$RHS)>>;
1062defm t2STRH:T2I_st<0b01,"strh",BinOpFrag<(truncstorei16 node:$LHS, node:$RHS)>>;
1063
1064// Store doubleword
1065let mayLoad = 1, neverHasSideEffects = 1, hasExtraSrcRegAllocReq = 1 in
1066def t2STRDi8 : T2Ii8s4<1, 0, 0, (outs),
1067                       (ins GPR:$src1, GPR:$src2, t2addrmode_imm8s4:$addr),
1068               IIC_iStorer, "strd", "\t$src1, $addr", []>;
1069
1070// Indexed stores
1071def t2STR_PRE  : T2Iidxldst<0, 0b10, 0, 1, (outs GPR:$base_wb),
1072                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1073                            AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
1074                         "str", "\t$src, [$base, $offset]!", "$base = $base_wb",
1075             [(set GPR:$base_wb,
1076                   (pre_store GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1077
1078def t2STR_POST : T2Iidxldst<0, 0b10, 0, 0, (outs GPR:$base_wb),
1079                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1080                            AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
1081                          "str", "\t$src, [$base], $offset", "$base = $base_wb",
1082             [(set GPR:$base_wb,
1083                  (post_store GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1084
1085def t2STRH_PRE  : T2Iidxldst<0, 0b01, 0, 1, (outs GPR:$base_wb),
1086                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1087                            AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
1088                        "strh", "\t$src, [$base, $offset]!", "$base = $base_wb",
1089        [(set GPR:$base_wb,
1090              (pre_truncsti16 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1091
1092def t2STRH_POST : T2Iidxldst<0, 0b01, 0, 0, (outs GPR:$base_wb),
1093                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1094                            AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
1095                         "strh", "\t$src, [$base], $offset", "$base = $base_wb",
1096       [(set GPR:$base_wb,
1097             (post_truncsti16 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1098
1099def t2STRB_PRE  : T2Iidxldst<0, 0b00, 0, 1, (outs GPR:$base_wb),
1100                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1101                            AddrModeT2_i8, IndexModePre, IIC_iStoreiu,
1102                        "strb", "\t$src, [$base, $offset]!", "$base = $base_wb",
1103         [(set GPR:$base_wb,
1104               (pre_truncsti8 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1105
1106def t2STRB_POST : T2Iidxldst<0, 0b00, 0, 0, (outs GPR:$base_wb),
1107                            (ins GPR:$src, GPR:$base, t2am_imm8_offset:$offset),
1108                            AddrModeT2_i8, IndexModePost, IIC_iStoreiu,
1109                         "strb", "\t$src, [$base], $offset", "$base = $base_wb",
1110        [(set GPR:$base_wb,
1111              (post_truncsti8 GPR:$src, GPR:$base, t2am_imm8_offset:$offset))]>;
1112
1113// STRT, STRBT, STRHT all have offset mode (PUW=0b110) and are for disassembly
1114// only.
1115// Ref: A8.6.193 STR (immediate, Thumb) Encoding T4
1116class T2IstT<bits<2> type, string opc>
1117  : T2Ii8<(outs GPR:$src), (ins t2addrmode_imm8:$addr), IIC_iStorei, opc,
1118          "\t$src, $addr", []> {
1119  let Inst{31-27} = 0b11111;
1120  let Inst{26-25} = 0b00;
1121  let Inst{24} = 0; // not signed
1122  let Inst{23} = 0;
1123  let Inst{22-21} = type;
1124  let Inst{20} = 0; // store
1125  let Inst{11} = 1;
1126  let Inst{10-8} = 0b110; // PUW
1127}
1128
1129def t2STRT   : T2IstT<0b10, "strt">;
1130def t2STRBT  : T2IstT<0b00, "strbt">;
1131def t2STRHT  : T2IstT<0b01, "strht">;
1132
1133// ldrd / strd pre / post variants
1134// For disassembly only.
1135
1136def t2LDRD_PRE  : T2Ii8s4<1, 1, 1, (outs GPR:$dst1, GPR:$dst2),
1137                 (ins GPR:$base, t2am_imm8s4_offset:$imm), NoItinerary,
1138                 "ldrd", "\t$dst1, $dst2, [$base, $imm]!", []>;
1139
1140def t2LDRD_POST : T2Ii8s4<0, 1, 1, (outs GPR:$dst1, GPR:$dst2),
1141                 (ins GPR:$base, t2am_imm8s4_offset:$imm), NoItinerary,
1142                 "ldrd", "\t$dst1, $dst2, [$base], $imm", []>;
1143
1144def t2STRD_PRE  : T2Ii8s4<1, 1, 0, (outs),
1145                 (ins GPR:$src1, GPR:$src2, GPR:$base, t2am_imm8s4_offset:$imm),
1146                 NoItinerary, "strd", "\t$src1, $src2, [$base, $imm]!", []>;
1147
1148def t2STRD_POST : T2Ii8s4<0, 1, 0, (outs),
1149                 (ins GPR:$src1, GPR:$src2, GPR:$base, t2am_imm8s4_offset:$imm),
1150                 NoItinerary, "strd", "\t$src1, $src2, [$base], $imm", []>;
1151
1152// T2Ipl (Preload Data/Instruction) signals the memory system of possible future
1153// data/instruction access.  These are for disassembly only.
1154//
1155// A8.6.117, A8.6.118.  Different instructions are generated for #0 and #-0.
1156// The neg_zero operand translates -0 to -1, -1 to -2, ..., etc.
1157multiclass T2Ipl<bit instr, bit write, string opc> {
1158
1159  def i12 : T2I<(outs), (ins GPR:$base, i32imm:$imm), IIC_iLoadi, opc,
1160                "\t[$base, $imm]", []> {
1161    let Inst{31-25} = 0b1111100;
1162    let Inst{24} = instr;
1163    let Inst{23} = 1; // U = 1
1164    let Inst{22} = 0;
1165    let Inst{21} = write;
1166    let Inst{20} = 1;
1167    let Inst{15-12} = 0b1111;
1168  }
1169
1170  def i8 : T2I<(outs), (ins GPR:$base, neg_zero:$imm), IIC_iLoadi, opc,
1171                "\t[$base, $imm]", []> {
1172    let Inst{31-25} = 0b1111100;
1173    let Inst{24} = instr;
1174    let Inst{23} = 0; // U = 0
1175    let Inst{22} = 0;
1176    let Inst{21} = write;
1177    let Inst{20} = 1;
1178    let Inst{15-12} = 0b1111;
1179    let Inst{11-8} = 0b1100;
1180  }
1181
1182  def pci : T2I<(outs), (ins GPR:$base, neg_zero:$imm), IIC_iLoadi, opc,
1183                "\t[pc, $imm]", []> {
1184    let Inst{31-25} = 0b1111100;
1185    let Inst{24} = instr;
1186    let Inst{23} = ?; // add = (U == 1)
1187    let Inst{22} = 0;
1188    let Inst{21} = write;
1189    let Inst{20} = 1;
1190    let Inst{19-16} = 0b1111; // Rn = 0b1111
1191    let Inst{15-12} = 0b1111;
1192  }
1193
1194  def r   : T2I<(outs), (ins GPR:$base, GPR:$a), IIC_iLoadi, opc,
1195                "\t[$base, $a]", []> {
1196    let Inst{31-25} = 0b1111100;
1197    let Inst{24} = instr;
1198    let Inst{23} = 0; // add = TRUE for T1
1199    let Inst{22} = 0;
1200    let Inst{21} = write;
1201    let Inst{20} = 1;
1202    let Inst{15-12} = 0b1111;
1203    let Inst{11-6} = 0000000;
1204    let Inst{5-4} = 0b00; // no shift is applied
1205  }
1206
1207  def s   : T2I<(outs), (ins GPR:$base, GPR:$a, i32imm:$shamt), IIC_iLoadi, opc,
1208                "\t[$base, $a, lsl $shamt]", []> {
1209    let Inst{31-25} = 0b1111100;
1210    let Inst{24} = instr;
1211    let Inst{23} = 0; // add = TRUE for T1
1212    let Inst{22} = 0;
1213    let Inst{21} = write;
1214    let Inst{20} = 1;
1215    let Inst{15-12} = 0b1111;
1216    let Inst{11-6} = 0000000;
1217  }
1218}
1219
1220defm t2PLD  : T2Ipl<0, 0, "pld">;
1221defm t2PLDW : T2Ipl<0, 1, "pldw">;
1222defm t2PLI  : T2Ipl<1, 0, "pli">;
1223
1224//===----------------------------------------------------------------------===//
1225//  Load / store multiple Instructions.
1226//
1227
1228let mayLoad = 1, neverHasSideEffects = 1, hasExtraDefRegAllocReq = 1 in {
1229def t2LDM : T2XI<(outs), (ins addrmode4:$addr, pred:$p,
1230                          reglist:$dsts, variable_ops), IIC_iLoadm,
1231                 "ldm${addr:submode}${p}${addr:wide}\t$addr, $dsts", []> {
1232  let Inst{31-27} = 0b11101;
1233  let Inst{26-25} = 0b00;
1234  let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1235  let Inst{22} = 0;
1236  let Inst{21} = 0; // The W bit.
1237  let Inst{20} = 1; // Load
1238}
1239
1240def t2LDM_UPD : T2XIt<(outs GPR:$wb), (ins addrmode4:$addr, pred:$p,
1241                                       reglist:$dsts, variable_ops), IIC_iLoadm,
1242                      "ldm${addr:submode}${p}${addr:wide}\t$addr!, $dsts",
1243                      "$addr.addr = $wb", []> {
1244  let Inst{31-27} = 0b11101;
1245  let Inst{26-25} = 0b00;
1246  let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1247  let Inst{22} = 0;
1248  let Inst{21} = 1; // The W bit.
1249  let Inst{20} = 1; // Load
1250}
1251} // mayLoad, neverHasSideEffects, hasExtraDefRegAllocReq
1252
1253let mayStore = 1, neverHasSideEffects = 1, hasExtraSrcRegAllocReq = 1 in {
1254def t2STM : T2XI<(outs), (ins addrmode4:$addr, pred:$p,
1255                          reglist:$srcs, variable_ops), IIC_iStorem,
1256                 "stm${addr:submode}${p}${addr:wide}\t$addr, $srcs", []> {
1257  let Inst{31-27} = 0b11101;
1258  let Inst{26-25} = 0b00;
1259  let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1260  let Inst{22} = 0;
1261  let Inst{21} = 0; // The W bit.
1262  let Inst{20} = 0; // Store
1263}
1264
1265def t2STM_UPD : T2XIt<(outs GPR:$wb), (ins addrmode4:$addr, pred:$p,
1266                                       reglist:$srcs, variable_ops),
1267                      IIC_iStorem,
1268                      "stm${addr:submode}${p}${addr:wide}\t$addr!, $srcs",
1269                      "$addr.addr = $wb", []> {
1270  let Inst{31-27} = 0b11101;
1271  let Inst{26-25} = 0b00;
1272  let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
1273  let Inst{22} = 0;
1274  let Inst{21} = 1; // The W bit.
1275  let Inst{20} = 0; // Store
1276}
1277} // mayStore, neverHasSideEffects, hasExtraSrcRegAllocReq
1278
1279//===----------------------------------------------------------------------===//
1280//  Move Instructions.
1281//
1282
1283let neverHasSideEffects = 1 in
1284def t2MOVr : T2sI<(outs GPR:$dst), (ins GPR:$src), IIC_iMOVr,
1285                   "mov", ".w\t$dst, $src", []> {
1286  let Inst{31-27} = 0b11101;
1287  let Inst{26-25} = 0b01;
1288  let Inst{24-21} = 0b0010;
1289  let Inst{20} = ?; // The S bit.
1290  let Inst{19-16} = 0b1111; // Rn
1291  let Inst{14-12} = 0b000;
1292  let Inst{7-4} = 0b0000;
1293}
1294
1295// AddedComplexity to ensure isel tries t2MOVi before t2MOVi16.
1296let isReMaterializable = 1, isAsCheapAsAMove = 1, AddedComplexity = 1 in
1297def t2MOVi : T2sI<(outs rGPR:$dst), (ins t2_so_imm:$src), IIC_iMOVi,
1298                   "mov", ".w\t$dst, $src",
1299                   [(set rGPR:$dst, t2_so_imm:$src)]> {
1300  let Inst{31-27} = 0b11110;
1301  let Inst{25} = 0;
1302  let Inst{24-21} = 0b0010;
1303  let Inst{20} = ?; // The S bit.
1304  let Inst{19-16} = 0b1111; // Rn
1305  let Inst{15} = 0;
1306}
1307
1308let isReMaterializable = 1, isAsCheapAsAMove = 1 in
1309def t2MOVi16 : T2I<(outs rGPR:$dst), (ins i32imm:$src), IIC_iMOVi,
1310                   "movw", "\t$dst, $src",
1311                   [(set rGPR:$dst, imm0_65535:$src)]> {
1312  let Inst{31-27} = 0b11110;
1313  let Inst{25} = 1;
1314  let Inst{24-21} = 0b0010;
1315  let Inst{20} = 0; // The S bit.
1316  let Inst{15} = 0;
1317}
1318
1319let Constraints = "$src = $dst" in
1320def t2MOVTi16 : T2I<(outs rGPR:$dst), (ins rGPR:$src, i32imm:$imm), IIC_iMOVi,
1321                    "movt", "\t$dst, $imm",
1322                    [(set rGPR:$dst,
1323                          (or (and rGPR:$src, 0xffff), lo16AllZero:$imm))]> {
1324  let Inst{31-27} = 0b11110;
1325  let Inst{25} = 1;
1326  let Inst{24-21} = 0b0110;
1327  let Inst{20} = 0; // The S bit.
1328  let Inst{15} = 0;
1329}
1330
1331def : T2Pat<(or rGPR:$src, 0xffff0000), (t2MOVTi16 rGPR:$src, 0xffff)>;
1332
1333//===----------------------------------------------------------------------===//
1334//  Extend Instructions.
1335//
1336
1337// Sign extenders
1338
1339defm t2SXTB  : T2I_unary_rrot<0b100, "sxtb",
1340                              UnOpFrag<(sext_inreg node:$Src, i8)>>;
1341defm t2SXTH  : T2I_unary_rrot<0b000, "sxth",
1342                              UnOpFrag<(sext_inreg node:$Src, i16)>>;
1343defm t2SXTB16 : T2I_unary_rrot_sxtb16<0b010, "sxtb16">;
1344
1345defm t2SXTAB : T2I_bin_rrot<0b100, "sxtab",
1346                        BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS, i8))>>;
1347defm t2SXTAH : T2I_bin_rrot<0b000, "sxtah",
1348                        BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS,i16))>>;
1349defm t2SXTAB16 : T2I_bin_rrot_DO<0b010, "sxtab16">;
1350
1351// TODO: SXT(A){B|H}16 - done for disassembly only
1352
1353// Zero extenders
1354
1355let AddedComplexity = 16 in {
1356defm t2UXTB   : T2I_unary_rrot<0b101, "uxtb",
1357                               UnOpFrag<(and node:$Src, 0x000000FF)>>;
1358defm t2UXTH   : T2I_unary_rrot<0b001, "uxth",
1359                               UnOpFrag<(and node:$Src, 0x0000FFFF)>>;
1360defm t2UXTB16 : T2I_unary_rrot_uxtb16<0b011, "uxtb16",
1361                               UnOpFrag<(and node:$Src, 0x00FF00FF)>>;
1362
1363// FIXME: This pattern incorrectly assumes the shl operator is a rotate.
1364//        The transformation should probably be done as a combiner action
1365//        instead so we can include a check for masking back in the upper
1366//        eight bits of the source into the lower eight bits of the result.
1367//def : T2Pat<(and (shl rGPR:$Src, (i32 8)), 0xFF00FF),
1368//            (t2UXTB16r_rot rGPR:$Src, 24)>, Requires<[HasT2ExtractPack]>;
1369def : T2Pat<(and (srl rGPR:$Src, (i32 8)), 0xFF00FF),
1370            (t2UXTB16r_rot rGPR:$Src, 8)>, Requires<[HasT2ExtractPack]>;
1371
1372defm t2UXTAB : T2I_bin_rrot<0b101, "uxtab",
1373                           BinOpFrag<(add node:$LHS, (and node:$RHS, 0x00FF))>>;
1374defm t2UXTAH : T2I_bin_rrot<0b001, "uxtah",
1375                           BinOpFrag<(add node:$LHS, (and node:$RHS, 0xFFFF))>>;
1376defm t2UXTAB16 : T2I_bin_rrot_DO<0b011, "uxtab16">;
1377}
1378
1379//===----------------------------------------------------------------------===//
1380//  Arithmetic Instructions.
1381//
1382
1383defm t2ADD  : T2I_bin_ii12rs<0b000, "add",
1384                             BinOpFrag<(add  node:$LHS, node:$RHS)>, 1>;
1385defm t2SUB  : T2I_bin_ii12rs<0b101, "sub",
1386                             BinOpFrag<(sub  node:$LHS, node:$RHS)>>;
1387
1388// ADD and SUB with 's' bit set. No 12-bit immediate (T4) variants.
1389defm t2ADDS : T2I_bin_s_irs <0b1000, "add",
1390                             BinOpFrag<(addc node:$LHS, node:$RHS)>, 1>;
1391defm t2SUBS : T2I_bin_s_irs <0b1101, "sub",
1392                             BinOpFrag<(subc node:$LHS, node:$RHS)>>;
1393
1394defm t2ADC  : T2I_adde_sube_irs<0b1010, "adc",
1395                          BinOpFrag<(adde_dead_carry node:$LHS, node:$RHS)>, 1>;
1396defm t2SBC  : T2I_adde_sube_irs<0b1011, "sbc",
1397                          BinOpFrag<(sube_dead_carry node:$LHS, node:$RHS)>>;
1398defm t2ADCS : T2I_adde_sube_s_irs<0b1010, "adc",
1399                          BinOpFrag<(adde_live_carry node:$LHS, node:$RHS)>, 1>;
1400defm t2SBCS : T2I_adde_sube_s_irs<0b1011, "sbc",
1401                          BinOpFrag<(sube_live_carry node:$LHS, node:$RHS)>>;
1402
1403// RSB
1404defm t2RSB  : T2I_rbin_irs  <0b1110, "rsb",
1405                             BinOpFrag<(sub  node:$LHS, node:$RHS)>>;
1406defm t2RSBS : T2I_rbin_s_is <0b1110, "rsb",
1407                             BinOpFrag<(subc node:$LHS, node:$RHS)>>;
1408
1409// (sub X, imm) gets canonicalized to (add X, -imm).  Match this form.
1410// The assume-no-carry-in form uses the negation of the input since add/sub
1411// assume opposite meanings of the carry flag (i.e., carry == !borrow).
1412// See the definition of AddWithCarry() in the ARM ARM A2.2.1 for the gory
1413// details.
1414// The AddedComplexity preferences the first variant over the others since
1415// it can be shrunk to a 16-bit wide encoding, while the others cannot.
1416let AddedComplexity = 1 in
1417def : T2Pat<(add        GPR:$src, imm0_255_neg:$imm),
1418            (t2SUBri    GPR:$src, imm0_255_neg:$imm)>;
1419def : T2Pat<(add        GPR:$src, t2_so_imm_neg:$imm),
1420            (t2SUBri    GPR:$src, t2_so_imm_neg:$imm)>;
1421def : T2Pat<(add        GPR:$src, imm0_4095_neg:$imm),
1422            (t2SUBri12  GPR:$src, imm0_4095_neg:$imm)>;
1423let AddedComplexity = 1 in
1424def : T2Pat<(addc       rGPR:$src, imm0_255_neg:$imm),
1425            (t2SUBSri   rGPR:$src, imm0_255_neg:$imm)>;
1426def : T2Pat<(addc       rGPR:$src, t2_so_imm_neg:$imm),
1427            (t2SUBSri   rGPR:$src, t2_so_imm_neg:$imm)>;
1428// The with-carry-in form matches bitwise not instead of the negation.
1429// Effectively, the inverse interpretation of the carry flag already accounts
1430// for part of the negation.
1431let AddedComplexity = 1 in
1432def : T2Pat<(adde       rGPR:$src, imm0_255_not:$imm),
1433            (t2SBCSri   rGPR:$src, imm0_255_not:$imm)>;
1434def : T2Pat<(adde       rGPR:$src, t2_so_imm_not:$imm),
1435            (t2SBCSri   rGPR:$src, t2_so_imm_not:$imm)>;
1436
1437// Select Bytes -- for disassembly only
1438
1439def t2SEL : T2I<(outs GPR:$dst), (ins GPR:$a, GPR:$b), NoItinerary, "sel",
1440                "\t$dst, $a, $b", []> {
1441  let Inst{31-27} = 0b11111;
1442  let Inst{26-24} = 0b010;
1443  let Inst{23} = 0b1;
1444  let Inst{22-20} = 0b010;
1445  let Inst{15-12} = 0b1111;
1446  let Inst{7} = 0b1;
1447  let Inst{6-4} = 0b000;
1448}
1449
1450// A6.3.13, A6.3.14, A6.3.15 Parallel addition and subtraction (signed/unsigned)
1451// And Miscellaneous operations -- for disassembly only
1452class T2I_pam<bits<3> op22_20, bits<4> op7_4, string opc,
1453              list<dag> pat = [/* For disassembly only; pattern left blank */]>
1454  : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), NoItinerary, opc,
1455        "\t$dst, $a, $b", pat> {
1456  let Inst{31-27} = 0b11111;
1457  let Inst{26-23} = 0b0101;
1458  let Inst{22-20} = op22_20;
1459  let Inst{15-12} = 0b1111;
1460  let Inst{7-4} = op7_4;
1461}
1462
1463// Saturating add/subtract -- for disassembly only
1464
1465def t2QADD    : T2I_pam<0b000, 0b1000, "qadd",
1466                        [(set rGPR:$dst, (int_arm_qadd rGPR:$a, rGPR:$b))]>;
1467def t2QADD16  : T2I_pam<0b001, 0b0001, "qadd16">;
1468def t2QADD8   : T2I_pam<0b000, 0b0001, "qadd8">;
1469def t2QASX    : T2I_pam<0b010, 0b0001, "qasx">;
1470def t2QDADD   : T2I_pam<0b000, 0b1001, "qdadd">;
1471def t2QDSUB   : T2I_pam<0b000, 0b1011, "qdsub">;
1472def t2QSAX    : T2I_pam<0b110, 0b0001, "qsax">;
1473def t2QSUB    : T2I_pam<0b000, 0b1010, "qsub",
1474                        [(set rGPR:$dst, (int_arm_qsub rGPR:$a, rGPR:$b))]>;
1475def t2QSUB16  : T2I_pam<0b101, 0b0001, "qsub16">;
1476def t2QSUB8   : T2I_pam<0b100, 0b0001, "qsub8">;
1477def t2UQADD16 : T2I_pam<0b001, 0b0101, "uqadd16">;
1478def t2UQADD8  : T2I_pam<0b000, 0b0101, "uqadd8">;
1479def t2UQASX   : T2I_pam<0b010, 0b0101, "uqasx">;
1480def t2UQSAX   : T2I_pam<0b110, 0b0101, "uqsax">;
1481def t2UQSUB16 : T2I_pam<0b101, 0b0101, "uqsub16">;
1482def t2UQSUB8  : T2I_pam<0b100, 0b0101, "uqsub8">;
1483
1484// Signed/Unsigned add/subtract -- for disassembly only
1485
1486def t2SASX    : T2I_pam<0b010, 0b0000, "sasx">;
1487def t2SADD16  : T2I_pam<0b001, 0b0000, "sadd16">;
1488def t2SADD8   : T2I_pam<0b000, 0b0000, "sadd8">;
1489def t2SSAX    : T2I_pam<0b110, 0b0000, "ssax">;
1490def t2SSUB16  : T2I_pam<0b101, 0b0000, "ssub16">;
1491def t2SSUB8   : T2I_pam<0b100, 0b0000, "ssub8">;
1492def t2UASX    : T2I_pam<0b010, 0b0100, "uasx">;
1493def t2UADD16  : T2I_pam<0b001, 0b0100, "uadd16">;
1494def t2UADD8   : T2I_pam<0b000, 0b0100, "uadd8">;
1495def t2USAX    : T2I_pam<0b110, 0b0100, "usax">;
1496def t2USUB16  : T2I_pam<0b101, 0b0100, "usub16">;
1497def t2USUB8   : T2I_pam<0b100, 0b0100, "usub8">;
1498
1499// Signed/Unsigned halving add/subtract -- for disassembly only
1500
1501def t2SHASX   : T2I_pam<0b010, 0b0010, "shasx">;
1502def t2SHADD16 : T2I_pam<0b001, 0b0010, "shadd16">;
1503def t2SHADD8  : T2I_pam<0b000, 0b0010, "shadd8">;
1504def t2SHSAX   : T2I_pam<0b110, 0b0010, "shsax">;
1505def t2SHSUB16 : T2I_pam<0b101, 0b0010, "shsub16">;
1506def t2SHSUB8  : T2I_pam<0b100, 0b0010, "shsub8">;
1507def t2UHASX   : T2I_pam<0b010, 0b0110, "uhasx">;
1508def t2UHADD16 : T2I_pam<0b001, 0b0110, "uhadd16">;
1509def t2UHADD8  : T2I_pam<0b000, 0b0110, "uhadd8">;
1510def t2UHSAX   : T2I_pam<0b110, 0b0110, "uhsax">;
1511def t2UHSUB16 : T2I_pam<0b101, 0b0110, "uhsub16">;
1512def t2UHSUB8  : T2I_pam<0b100, 0b0110, "uhsub8">;
1513
1514// Unsigned Sum of Absolute Differences [and Accumulate] -- for disassembly only
1515
1516def t2USAD8   : T2I_mac<0, 0b111, 0b0000, (outs rGPR:$dst),
1517                                           (ins rGPR:$a, rGPR:$b),
1518                        NoItinerary, "usad8", "\t$dst, $a, $b", []> {
1519  let Inst{15-12} = 0b1111;
1520}
1521def t2USADA8  : T2I_mac<0, 0b111, 0b0000, (outs rGPR:$dst),
1522                       (ins rGPR:$a, rGPR:$b, rGPR:$acc), NoItinerary, "usada8",
1523                        "\t$dst, $a, $b, $acc", []>;
1524
1525// Signed/Unsigned saturate -- for disassembly only
1526
1527def t2SSAT: T2I<(outs rGPR:$dst), (ins i32imm:$bit_pos, rGPR:$a, shift_imm:$sh),
1528                NoItinerary, "ssat", "\t$dst, $bit_pos, $a$sh",
1529                [/* For disassembly only; pattern left blank */]> {
1530  let Inst{31-27} = 0b11110;
1531  let Inst{25-22} = 0b1100;
1532  let Inst{20} = 0;
1533  let Inst{15} = 0;
1534}
1535
1536def t2SSAT16: T2I<(outs rGPR:$dst), (ins i32imm:$bit_pos, rGPR:$a), NoItinerary,
1537                   "ssat16", "\t$dst, $bit_pos, $a",
1538                   [/* For disassembly only; pattern left blank */]> {
1539  let Inst{31-27} = 0b11110;
1540  let Inst{25-22} = 0b1100;
1541  let Inst{20} = 0;
1542  let Inst{15} = 0;
1543  let Inst{21} = 1;        // sh = '1'
1544  let Inst{14-12} = 0b000; // imm3 = '000'
1545  let Inst{7-6} = 0b00;    // imm2 = '00'
1546}
1547
1548def t2USAT: T2I<(outs rGPR:$dst), (ins i32imm:$bit_pos, rGPR:$a, shift_imm:$sh),
1549                NoItinerary, "usat", "\t$dst, $bit_pos, $a$sh",
1550                [/* For disassembly only; pattern left blank */]> {
1551  let Inst{31-27} = 0b11110;
1552  let Inst{25-22} = 0b1110;
1553  let Inst{20} = 0;
1554  let Inst{15} = 0;
1555}
1556
1557def t2USAT16: T2I<(outs rGPR:$dst), (ins i32imm:$bit_pos, rGPR:$a), NoItinerary,
1558                   "usat16", "\t$dst, $bit_pos, $a",
1559                   [/* For disassembly only; pattern left blank */]> {
1560  let Inst{31-27} = 0b11110;
1561  let Inst{25-22} = 0b1110;
1562  let Inst{20} = 0;
1563  let Inst{15} = 0;
1564  let Inst{21} = 1;        // sh = '1'
1565  let Inst{14-12} = 0b000; // imm3 = '000'
1566  let Inst{7-6} = 0b00;    // imm2 = '00'
1567}
1568
1569def : T2Pat<(int_arm_ssat GPR:$a, imm:$pos), (t2SSAT imm:$pos, GPR:$a, 0)>;
1570def : T2Pat<(int_arm_usat GPR:$a, imm:$pos), (t2USAT imm:$pos, GPR:$a, 0)>;
1571
1572//===----------------------------------------------------------------------===//
1573//  Shift and rotate Instructions.
1574//
1575
1576defm t2LSL  : T2I_sh_ir<0b00, "lsl", BinOpFrag<(shl  node:$LHS, node:$RHS)>>;
1577defm t2LSR  : T2I_sh_ir<0b01, "lsr", BinOpFrag<(srl  node:$LHS, node:$RHS)>>;
1578defm t2ASR  : T2I_sh_ir<0b10, "asr", BinOpFrag<(sra  node:$LHS, node:$RHS)>>;
1579defm t2ROR  : T2I_sh_ir<0b11, "ror", BinOpFrag<(rotr node:$LHS, node:$RHS)>>;
1580
1581let Uses = [CPSR] in {
1582def t2MOVrx : T2sI<(outs rGPR:$dst), (ins rGPR:$src), IIC_iMOVsi,
1583                   "rrx", "\t$dst, $src",
1584                   [(set rGPR:$dst, (ARMrrx rGPR:$src))]> {
1585  let Inst{31-27} = 0b11101;
1586  let Inst{26-25} = 0b01;
1587  let Inst{24-21} = 0b0010;
1588  let Inst{20} = ?; // The S bit.
1589  let Inst{19-16} = 0b1111; // Rn
1590  let Inst{14-12} = 0b000;
1591  let Inst{7-4} = 0b0011;
1592}
1593}
1594
1595let Defs = [CPSR] in {
1596def t2MOVsrl_flag : T2I<(outs rGPR:$dst), (ins rGPR:$src), IIC_iMOVsi,
1597                        "lsrs", ".w\t$dst, $src, #1",
1598                        [(set rGPR:$dst, (ARMsrl_flag rGPR:$src))]> {
1599  let Inst{31-27} = 0b11101;
1600  let Inst{26-25} = 0b01;
1601  let Inst{24-21} = 0b0010;
1602  let Inst{20} = 1; // The S bit.
1603  let Inst{19-16} = 0b1111; // Rn
1604  let Inst{5-4} = 0b01; // Shift type.
1605  // Shift amount = Inst{14-12:7-6} = 1.
1606  let Inst{14-12} = 0b000;
1607  let Inst{7-6} = 0b01;
1608}
1609def t2MOVsra_flag : T2I<(outs rGPR:$dst), (ins rGPR:$src), IIC_iMOVsi,
1610                        "asrs", ".w\t$dst, $src, #1",
1611                        [(set rGPR:$dst, (ARMsra_flag rGPR:$src))]> {
1612  let Inst{31-27} = 0b11101;
1613  let Inst{26-25} = 0b01;
1614  let Inst{24-21} = 0b0010;
1615  let Inst{20} = 1; // The S bit.
1616  let Inst{19-16} = 0b1111; // Rn
1617  let Inst{5-4} = 0b10; // Shift type.
1618  // Shift amount = Inst{14-12:7-6} = 1.
1619  let Inst{14-12} = 0b000;
1620  let Inst{7-6} = 0b01;
1621}
1622}
1623
1624//===----------------------------------------------------------------------===//
1625//  Bitwise Instructions.
1626//
1627
1628defm t2AND  : T2I_bin_w_irs<0b0000, "and",
1629                            BinOpFrag<(and node:$LHS, node:$RHS)>, 1>;
1630defm t2ORR  : T2I_bin_w_irs<0b0010, "orr",
1631                            BinOpFrag<(or  node:$LHS, node:$RHS)>, 1>;
1632defm t2EOR  : T2I_bin_w_irs<0b0100, "eor",
1633                            BinOpFrag<(xor node:$LHS, node:$RHS)>, 1>;
1634
1635defm t2BIC  : T2I_bin_w_irs<0b0001, "bic",
1636                            BinOpFrag<(and node:$LHS, (not node:$RHS))>>;
1637
1638defm t2ANDS : T2I_bin_s_irs<0b0000, "and",
1639                            BinOpFrag<(ARMand node:$LHS, node:$RHS)>, 1>;
1640
1641let Constraints = "$src = $dst" in
1642def t2BFC : T2I<(outs rGPR:$dst), (ins rGPR:$src, bf_inv_mask_imm:$imm),
1643                IIC_iUNAsi, "bfc", "\t$dst, $imm",
1644                [(set rGPR:$dst, (and rGPR:$src, bf_inv_mask_imm:$imm))]> {
1645  let Inst{31-27} = 0b11110;
1646  let Inst{25} = 1;
1647  let Inst{24-20} = 0b10110;
1648  let Inst{19-16} = 0b1111; // Rn
1649  let Inst{15} = 0;
1650}
1651
1652def t2SBFX: T2I<(outs rGPR:$dst), (ins rGPR:$src, imm0_31:$lsb, imm0_31:$width),
1653                 IIC_iALUi, "sbfx", "\t$dst, $src, $lsb, $width", []> {
1654  let Inst{31-27} = 0b11110;
1655  let Inst{25} = 1;
1656  let Inst{24-20} = 0b10100;
1657  let Inst{15} = 0;
1658}
1659
1660def t2UBFX: T2I<(outs rGPR:$dst), (ins rGPR:$src, imm0_31:$lsb, imm0_31:$width),
1661                 IIC_iALUi, "ubfx", "\t$dst, $src, $lsb, $width", []> {
1662  let Inst{31-27} = 0b11110;
1663  let Inst{25} = 1;
1664  let Inst{24-20} = 0b11100;
1665  let Inst{15} = 0;
1666}
1667
1668// A8.6.18  BFI - Bitfield insert (Encoding T1)
1669let Constraints = "$src = $dst" in
1670def t2BFI : T2I<(outs rGPR:$dst),
1671                (ins rGPR:$src, rGPR:$val, bf_inv_mask_imm:$imm),
1672                IIC_iALUi, "bfi", "\t$dst, $val, $imm",
1673                [(set rGPR:$dst, (ARMbfi rGPR:$src, rGPR:$val,
1674                                 bf_inv_mask_imm:$imm))]> {
1675  let Inst{31-27} = 0b11110;
1676  let Inst{25} = 1;
1677  let Inst{24-20} = 0b10110;
1678  let Inst{15} = 0;
1679}
1680
1681defm t2ORN  : T2I_bin_irs<0b0011, "orn", BinOpFrag<(or  node:$LHS,
1682                          (not node:$RHS))>, 0, "">;
1683
1684// Prefer over of t2EORri ra, rb, -1 because mvn has 16-bit version
1685let AddedComplexity = 1 in
1686defm t2MVN  : T2I_un_irs <0b0011, "mvn", UnOpFrag<(not node:$Src)>, 1, 1>;
1687
1688
1689let AddedComplexity = 1 in
1690def : T2Pat<(and     rGPR:$src, t2_so_imm_not:$imm),
1691            (t2BICri rGPR:$src, t2_so_imm_not:$imm)>;
1692
1693// FIXME: Disable this pattern on Darwin to workaround an assembler bug.
1694def : T2Pat<(or      rGPR:$src, t2_so_imm_not:$imm),
1695            (t2ORNri rGPR:$src, t2_so_imm_not:$imm)>,
1696            Requires<[IsThumb2]>;
1697
1698def : T2Pat<(t2_so_imm_not:$src),
1699            (t2MVNi t2_so_imm_not:$src)>;
1700
1701//===----------------------------------------------------------------------===//
1702//  Multiply Instructions.
1703//
1704let isCommutable = 1 in
1705def t2MUL: T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1706                "mul", "\t$dst, $a, $b",
1707                [(set rGPR:$dst, (mul rGPR:$a, rGPR:$b))]> {
1708  let Inst{31-27} = 0b11111;
1709  let Inst{26-23} = 0b0110;
1710  let Inst{22-20} = 0b000;
1711  let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1712  let Inst{7-4} = 0b0000; // Multiply
1713}
1714
1715def t2MLA: T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1716		"mla", "\t$dst, $a, $b, $c",
1717		[(set rGPR:$dst, (add (mul rGPR:$a, rGPR:$b), rGPR:$c))]> {
1718  let Inst{31-27} = 0b11111;
1719  let Inst{26-23} = 0b0110;
1720  let Inst{22-20} = 0b000;
1721  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1722  let Inst{7-4} = 0b0000; // Multiply
1723}
1724
1725def t2MLS: T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1726		"mls", "\t$dst, $a, $b, $c",
1727                [(set rGPR:$dst, (sub rGPR:$c, (mul rGPR:$a, rGPR:$b)))]> {
1728  let Inst{31-27} = 0b11111;
1729  let Inst{26-23} = 0b0110;
1730  let Inst{22-20} = 0b000;
1731  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1732  let Inst{7-4} = 0b0001; // Multiply and Subtract
1733}
1734
1735// Extra precision multiplies with low / high results
1736let neverHasSideEffects = 1 in {
1737let isCommutable = 1 in {
1738def t2SMULL : T2I<(outs rGPR:$ldst, rGPR:$hdst),
1739                  (ins rGPR:$a, rGPR:$b), IIC_iMUL64,
1740                   "smull", "\t$ldst, $hdst, $a, $b", []> {
1741  let Inst{31-27} = 0b11111;
1742  let Inst{26-23} = 0b0111;
1743  let Inst{22-20} = 0b000;
1744  let Inst{7-4} = 0b0000;
1745}
1746
1747def t2UMULL : T2I<(outs rGPR:$ldst, rGPR:$hdst),
1748                  (ins rGPR:$a, rGPR:$b), IIC_iMUL64,
1749                   "umull", "\t$ldst, $hdst, $a, $b", []> {
1750  let Inst{31-27} = 0b11111;
1751  let Inst{26-23} = 0b0111;
1752  let Inst{22-20} = 0b010;
1753  let Inst{7-4} = 0b0000;
1754}
1755} // isCommutable
1756
1757// Multiply + accumulate
1758def t2SMLAL : T2I<(outs rGPR:$ldst, rGPR:$hdst),
1759                  (ins rGPR:$a, rGPR:$b), IIC_iMAC64,
1760                  "smlal", "\t$ldst, $hdst, $a, $b", []>{
1761  let Inst{31-27} = 0b11111;
1762  let Inst{26-23} = 0b0111;
1763  let Inst{22-20} = 0b100;
1764  let Inst{7-4} = 0b0000;
1765}
1766
1767def t2UMLAL : T2I<(outs rGPR:$ldst, rGPR:$hdst),
1768                  (ins rGPR:$a, rGPR:$b), IIC_iMAC64,
1769                  "umlal", "\t$ldst, $hdst, $a, $b", []>{
1770  let Inst{31-27} = 0b11111;
1771  let Inst{26-23} = 0b0111;
1772  let Inst{22-20} = 0b110;
1773  let Inst{7-4} = 0b0000;
1774}
1775
1776def t2UMAAL : T2I<(outs rGPR:$ldst, rGPR:$hdst),
1777                  (ins rGPR:$a, rGPR:$b), IIC_iMAC64,
1778                  "umaal", "\t$ldst, $hdst, $a, $b", []>{
1779  let Inst{31-27} = 0b11111;
1780  let Inst{26-23} = 0b0111;
1781  let Inst{22-20} = 0b110;
1782  let Inst{7-4} = 0b0110;
1783}
1784} // neverHasSideEffects
1785
1786// Rounding variants of the below included for disassembly only
1787
1788// Most significant word multiply
1789def t2SMMUL : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1790                  "smmul", "\t$dst, $a, $b",
1791                  [(set rGPR:$dst, (mulhs rGPR:$a, rGPR:$b))]> {
1792  let Inst{31-27} = 0b11111;
1793  let Inst{26-23} = 0b0110;
1794  let Inst{22-20} = 0b101;
1795  let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1796  let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1797}
1798
1799def t2SMMULR : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1800                  "smmulr", "\t$dst, $a, $b", []> {
1801  let Inst{31-27} = 0b11111;
1802  let Inst{26-23} = 0b0110;
1803  let Inst{22-20} = 0b101;
1804  let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1805  let Inst{7-4} = 0b0001; // Rounding (Inst{4} = 1)
1806}
1807
1808def t2SMMLA : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1809                  "smmla", "\t$dst, $a, $b, $c",
1810                  [(set rGPR:$dst, (add (mulhs rGPR:$a, rGPR:$b), rGPR:$c))]> {
1811  let Inst{31-27} = 0b11111;
1812  let Inst{26-23} = 0b0110;
1813  let Inst{22-20} = 0b101;
1814  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1815  let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1816}
1817
1818def t2SMMLAR: T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1819                  "smmlar", "\t$dst, $a, $b, $c", []> {
1820  let Inst{31-27} = 0b11111;
1821  let Inst{26-23} = 0b0110;
1822  let Inst{22-20} = 0b101;
1823  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1824  let Inst{7-4} = 0b0001; // Rounding (Inst{4} = 1)
1825}
1826
1827def t2SMMLS: T2I <(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1828                   "smmls", "\t$dst, $a, $b, $c",
1829                   [(set rGPR:$dst, (sub rGPR:$c, (mulhs rGPR:$a, rGPR:$b)))]> {
1830  let Inst{31-27} = 0b11111;
1831  let Inst{26-23} = 0b0110;
1832  let Inst{22-20} = 0b110;
1833  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1834  let Inst{7-4} = 0b0000; // No Rounding (Inst{4} = 0)
1835}
1836
1837def t2SMMLSR:T2I <(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$c), IIC_iMAC32,
1838                   "smmlsr", "\t$dst, $a, $b, $c", []> {
1839  let Inst{31-27} = 0b11111;
1840  let Inst{26-23} = 0b0110;
1841  let Inst{22-20} = 0b110;
1842  let Inst{15-12} = {?, ?, ?, ?}; // Ra
1843  let Inst{7-4} = 0b0001; // Rounding (Inst{4} = 1)
1844}
1845
1846multiclass T2I_smul<string opc, PatFrag opnode> {
1847  def BB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1848              !strconcat(opc, "bb"), "\t$dst, $a, $b",
1849              [(set rGPR:$dst, (opnode (sext_inreg rGPR:$a, i16),
1850                                      (sext_inreg rGPR:$b, i16)))]> {
1851    let Inst{31-27} = 0b11111;
1852    let Inst{26-23} = 0b0110;
1853    let Inst{22-20} = 0b001;
1854    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1855    let Inst{7-6} = 0b00;
1856    let Inst{5-4} = 0b00;
1857  }
1858
1859  def BT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1860              !strconcat(opc, "bt"), "\t$dst, $a, $b",
1861              [(set rGPR:$dst, (opnode (sext_inreg rGPR:$a, i16),
1862                                      (sra rGPR:$b, (i32 16))))]> {
1863    let Inst{31-27} = 0b11111;
1864    let Inst{26-23} = 0b0110;
1865    let Inst{22-20} = 0b001;
1866    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1867    let Inst{7-6} = 0b00;
1868    let Inst{5-4} = 0b01;
1869  }
1870
1871  def TB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1872              !strconcat(opc, "tb"), "\t$dst, $a, $b",
1873              [(set rGPR:$dst, (opnode (sra rGPR:$a, (i32 16)),
1874                                      (sext_inreg rGPR:$b, i16)))]> {
1875    let Inst{31-27} = 0b11111;
1876    let Inst{26-23} = 0b0110;
1877    let Inst{22-20} = 0b001;
1878    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1879    let Inst{7-6} = 0b00;
1880    let Inst{5-4} = 0b10;
1881  }
1882
1883  def TT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL32,
1884              !strconcat(opc, "tt"), "\t$dst, $a, $b",
1885              [(set rGPR:$dst, (opnode (sra rGPR:$a, (i32 16)),
1886                                      (sra rGPR:$b, (i32 16))))]> {
1887    let Inst{31-27} = 0b11111;
1888    let Inst{26-23} = 0b0110;
1889    let Inst{22-20} = 0b001;
1890    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1891    let Inst{7-6} = 0b00;
1892    let Inst{5-4} = 0b11;
1893  }
1894
1895  def WB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL16,
1896              !strconcat(opc, "wb"), "\t$dst, $a, $b",
1897              [(set rGPR:$dst, (sra (opnode rGPR:$a,
1898                                    (sext_inreg rGPR:$b, i16)), (i32 16)))]> {
1899    let Inst{31-27} = 0b11111;
1900    let Inst{26-23} = 0b0110;
1901    let Inst{22-20} = 0b011;
1902    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1903    let Inst{7-6} = 0b00;
1904    let Inst{5-4} = 0b00;
1905  }
1906
1907  def WT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b), IIC_iMUL16,
1908              !strconcat(opc, "wt"), "\t$dst, $a, $b",
1909              [(set rGPR:$dst, (sra (opnode rGPR:$a,
1910                                    (sra rGPR:$b, (i32 16))), (i32 16)))]> {
1911    let Inst{31-27} = 0b11111;
1912    let Inst{26-23} = 0b0110;
1913    let Inst{22-20} = 0b011;
1914    let Inst{15-12} = 0b1111; // Ra = 0b1111 (no accumulate)
1915    let Inst{7-6} = 0b00;
1916    let Inst{5-4} = 0b01;
1917  }
1918}
1919
1920
1921multiclass T2I_smla<string opc, PatFrag opnode> {
1922  def BB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1923              !strconcat(opc, "bb"), "\t$dst, $a, $b, $acc",
1924              [(set rGPR:$dst, (add rGPR:$acc,
1925                               (opnode (sext_inreg rGPR:$a, i16),
1926                                       (sext_inreg rGPR:$b, i16))))]> {
1927    let Inst{31-27} = 0b11111;
1928    let Inst{26-23} = 0b0110;
1929    let Inst{22-20} = 0b001;
1930    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1931    let Inst{7-6} = 0b00;
1932    let Inst{5-4} = 0b00;
1933  }
1934
1935  def BT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1936             !strconcat(opc, "bt"), "\t$dst, $a, $b, $acc",
1937             [(set rGPR:$dst, (add rGPR:$acc, (opnode (sext_inreg rGPR:$a, i16),
1938                                                  (sra rGPR:$b, (i32 16)))))]> {
1939    let Inst{31-27} = 0b11111;
1940    let Inst{26-23} = 0b0110;
1941    let Inst{22-20} = 0b001;
1942    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1943    let Inst{7-6} = 0b00;
1944    let Inst{5-4} = 0b01;
1945  }
1946
1947  def TB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1948              !strconcat(opc, "tb"), "\t$dst, $a, $b, $acc",
1949              [(set rGPR:$dst, (add rGPR:$acc, (opnode (sra rGPR:$a, (i32 16)),
1950                                                (sext_inreg rGPR:$b, i16))))]> {
1951    let Inst{31-27} = 0b11111;
1952    let Inst{26-23} = 0b0110;
1953    let Inst{22-20} = 0b001;
1954    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1955    let Inst{7-6} = 0b00;
1956    let Inst{5-4} = 0b10;
1957  }
1958
1959  def TT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1960              !strconcat(opc, "tt"), "\t$dst, $a, $b, $acc",
1961             [(set rGPR:$dst, (add rGPR:$acc, (opnode (sra rGPR:$a, (i32 16)),
1962                                                  (sra rGPR:$b, (i32 16)))))]> {
1963    let Inst{31-27} = 0b11111;
1964    let Inst{26-23} = 0b0110;
1965    let Inst{22-20} = 0b001;
1966    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1967    let Inst{7-6} = 0b00;
1968    let Inst{5-4} = 0b11;
1969  }
1970
1971  def WB : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1972              !strconcat(opc, "wb"), "\t$dst, $a, $b, $acc",
1973              [(set rGPR:$dst, (add rGPR:$acc, (sra (opnode rGPR:$a,
1974                                     (sext_inreg rGPR:$b, i16)), (i32 16))))]> {
1975    let Inst{31-27} = 0b11111;
1976    let Inst{26-23} = 0b0110;
1977    let Inst{22-20} = 0b011;
1978    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1979    let Inst{7-6} = 0b00;
1980    let Inst{5-4} = 0b00;
1981  }
1982
1983  def WT : T2I<(outs rGPR:$dst), (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC16,
1984              !strconcat(opc, "wt"), "\t$dst, $a, $b, $acc",
1985              [(set rGPR:$dst, (add rGPR:$acc, (sra (opnode rGPR:$a,
1986                                       (sra rGPR:$b, (i32 16))), (i32 16))))]> {
1987    let Inst{31-27} = 0b11111;
1988    let Inst{26-23} = 0b0110;
1989    let Inst{22-20} = 0b011;
1990    let Inst{15-12} = {?, ?, ?, ?}; // Ra
1991    let Inst{7-6} = 0b00;
1992    let Inst{5-4} = 0b01;
1993  }
1994}
1995
1996defm t2SMUL : T2I_smul<"smul", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1997defm t2SMLA : T2I_smla<"smla", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1998
1999// Halfword multiple accumulate long: SMLAL<x><y> -- for disassembly only
2000def t2SMLALBB : T2I_mac<1, 0b100, 0b1000, (outs rGPR:$ldst,rGPR:$hdst),
2001         (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlalbb", "\t$ldst, $hdst, $a, $b",
2002           [/* For disassembly only; pattern left blank */]>;
2003def t2SMLALBT : T2I_mac<1, 0b100, 0b1001, (outs rGPR:$ldst,rGPR:$hdst),
2004         (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlalbt", "\t$ldst, $hdst, $a, $b",
2005           [/* For disassembly only; pattern left blank */]>;
2006def t2SMLALTB : T2I_mac<1, 0b100, 0b1010, (outs rGPR:$ldst,rGPR:$hdst),
2007         (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlaltb", "\t$ldst, $hdst, $a, $b",
2008           [/* For disassembly only; pattern left blank */]>;
2009def t2SMLALTT : T2I_mac<1, 0b100, 0b1011, (outs rGPR:$ldst,rGPR:$hdst),
2010         (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlaltt", "\t$ldst, $hdst, $a, $b",
2011           [/* For disassembly only; pattern left blank */]>;
2012
2013// Dual halfword multiple: SMUAD, SMUSD, SMLAD, SMLSD, SMLALD, SMLSLD
2014// These are for disassembly only.
2015
2016def t2SMUAD: T2I_mac<0, 0b010, 0b0000, (outs rGPR:$dst), (ins rGPR:$a, rGPR:$b),
2017                     IIC_iMAC32, "smuad", "\t$dst, $a, $b", []> {
2018  let Inst{15-12} = 0b1111;
2019}
2020def t2SMUADX:T2I_mac<0, 0b010, 0b0001, (outs rGPR:$dst), (ins rGPR:$a, rGPR:$b),
2021                     IIC_iMAC32, "smuadx", "\t$dst, $a, $b", []> {
2022  let Inst{15-12} = 0b1111;
2023}
2024def t2SMUSD: T2I_mac<0, 0b100, 0b0000, (outs rGPR:$dst), (ins rGPR:$a, rGPR:$b),
2025                     IIC_iMAC32, "smusd", "\t$dst, $a, $b", []> {
2026  let Inst{15-12} = 0b1111;
2027}
2028def t2SMUSDX:T2I_mac<0, 0b100, 0b0001, (outs rGPR:$dst), (ins rGPR:$a, rGPR:$b),
2029                     IIC_iMAC32, "smusdx", "\t$dst, $a, $b", []> {
2030  let Inst{15-12} = 0b1111;
2031}
2032def t2SMLAD   : T2I_mac<0, 0b010, 0b0000, (outs rGPR:$dst),
2033                        (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC32, "smlad",
2034                        "\t$dst, $a, $b, $acc", []>;
2035def t2SMLADX  : T2I_mac<0, 0b010, 0b0001, (outs rGPR:$dst),
2036                        (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC32, "smladx",
2037                        "\t$dst, $a, $b, $acc", []>;
2038def t2SMLSD   : T2I_mac<0, 0b100, 0b0000, (outs rGPR:$dst),
2039                        (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC32, "smlsd",
2040                        "\t$dst, $a, $b, $acc", []>;
2041def t2SMLSDX  : T2I_mac<0, 0b100, 0b0001, (outs rGPR:$dst),
2042                        (ins rGPR:$a, rGPR:$b, rGPR:$acc), IIC_iMAC32, "smlsdx",
2043                        "\t$dst, $a, $b, $acc", []>;
2044def t2SMLALD  : T2I_mac<1, 0b100, 0b1100, (outs rGPR:$ldst,rGPR:$hdst),
2045                        (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlald",
2046                        "\t$ldst, $hdst, $a, $b", []>;
2047def t2SMLALDX : T2I_mac<1, 0b100, 0b1101, (outs rGPR:$ldst,rGPR:$hdst),
2048                        (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlaldx",
2049                        "\t$ldst, $hdst, $a, $b", []>;
2050def t2SMLSLD  : T2I_mac<1, 0b101, 0b1100, (outs rGPR:$ldst,rGPR:$hdst),
2051                        (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlsld",
2052                        "\t$ldst, $hdst, $a, $b", []>;
2053def t2SMLSLDX : T2I_mac<1, 0b101, 0b1101, (outs rGPR:$ldst,rGPR:$hdst),
2054                        (ins rGPR:$a,rGPR:$b), IIC_iMAC64, "smlsldx",
2055                        "\t$ldst, $hdst, $a, $b", []>;
2056
2057//===----------------------------------------------------------------------===//
2058//  Misc. Arithmetic Instructions.
2059//
2060
2061class T2I_misc<bits<2> op1, bits<2> op2, dag oops, dag iops,
2062      InstrItinClass itin, string opc, string asm, list<dag> pattern>
2063  : T2I<oops, iops, itin, opc, asm, pattern> {
2064  let Inst{31-27} = 0b11111;
2065  let Inst{26-22} = 0b01010;
2066  let Inst{21-20} = op1;
2067  let Inst{15-12} = 0b1111;
2068  let Inst{7-6} = 0b10;
2069  let Inst{5-4} = op2;
2070}
2071
2072def t2CLZ : T2I_misc<0b11, 0b00, (outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
2073                    "clz", "\t$dst, $src", [(set rGPR:$dst, (ctlz rGPR:$src))]>;
2074
2075def t2RBIT : T2I_misc<0b01, 0b10, (outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
2076                      "rbit", "\t$dst, $src",
2077                      [(set rGPR:$dst, (ARMrbit rGPR:$src))]>;
2078
2079def t2REV : T2I_misc<0b01, 0b00, (outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
2080                 "rev", ".w\t$dst, $src", [(set rGPR:$dst, (bswap rGPR:$src))]>;
2081
2082def t2REV16 : T2I_misc<0b01, 0b01, (outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
2083                       "rev16", ".w\t$dst, $src",
2084                [(set rGPR:$dst,
2085                    (or (and (srl rGPR:$src, (i32 8)), 0xFF),
2086                        (or (and (shl rGPR:$src, (i32 8)), 0xFF00),
2087                            (or (and (srl rGPR:$src, (i32 8)), 0xFF0000),
2088                               (and (shl rGPR:$src, (i32 8)), 0xFF000000)))))]>;
2089
2090def t2REVSH : T2I_misc<0b01, 0b11, (outs rGPR:$dst), (ins rGPR:$src), IIC_iUNAr,
2091                       "revsh", ".w\t$dst, $src",
2092                 [(set rGPR:$dst,
2093                    (sext_inreg
2094                      (or (srl (and rGPR:$src, 0xFF00), (i32 8)),
2095                          (shl rGPR:$src, (i32 8))), i16))]>;
2096
2097def t2PKHBT : T2I<(outs rGPR:$dst), (ins rGPR:$src1, rGPR:$src2, shift_imm:$sh),
2098                  IIC_iALUsi, "pkhbt", "\t$dst, $src1, $src2$sh",
2099                  [(set rGPR:$dst, (or (and rGPR:$src1, 0xFFFF),
2100                                      (and (shl rGPR:$src2, lsl_amt:$sh),
2101                                           0xFFFF0000)))]>,
2102                  Requires<[HasT2ExtractPack]> {
2103  let Inst{31-27} = 0b11101;
2104  let Inst{26-25} = 0b01;
2105  let Inst{24-20} = 0b01100;
2106  let Inst{5} = 0; // BT form
2107  let Inst{4} = 0;
2108}
2109
2110// Alternate cases for PKHBT where identities eliminate some nodes.
2111def : T2Pat<(or (and rGPR:$src1, 0xFFFF), (and rGPR:$src2, 0xFFFF0000)),
2112            (t2PKHBT rGPR:$src1, rGPR:$src2, 0)>,
2113            Requires<[HasT2ExtractPack]>;
2114def : T2Pat<(or (and rGPR:$src1, 0xFFFF), (shl rGPR:$src2, imm16_31:$sh)),
2115            (t2PKHBT rGPR:$src1, rGPR:$src2, (lsl_shift_imm imm16_31:$sh))>,
2116            Requires<[HasT2ExtractPack]>;
2117
2118// Note: Shifts of 1-15 bits will be transformed to srl instead of sra and
2119// will match the pattern below.
2120def t2PKHTB : T2I<(outs rGPR:$dst), (ins rGPR:$src1, rGPR:$src2, shift_imm:$sh),
2121                  IIC_iALUsi, "pkhtb", "\t$dst, $src1, $src2$sh",
2122                  [(set rGPR:$dst, (or (and rGPR:$src1, 0xFFFF0000),
2123                                       (and (sra rGPR:$src2, asr_amt:$sh),
2124                                            0xFFFF)))]>,
2125                  Requires<[HasT2ExtractPack]> {
2126  let Inst{31-27} = 0b11101;
2127  let Inst{26-25} = 0b01;
2128  let Inst{24-20} = 0b01100;
2129  let Inst{5} = 1; // TB form
2130  let Inst{4} = 0;
2131}
2132
2133// Alternate cases for PKHTB where identities eliminate some nodes.  Note that
2134// a shift amount of 0 is *not legal* here, it is PKHBT instead.
2135def : T2Pat<(or (and rGPR:$src1, 0xFFFF0000), (srl rGPR:$src2, imm16_31:$sh)),
2136            (t2PKHTB rGPR:$src1, rGPR:$src2, (asr_shift_imm imm16_31:$sh))>,
2137            Requires<[HasT2ExtractPack]>;
2138def : T2Pat<(or (and rGPR:$src1, 0xFFFF0000),
2139                (and (srl rGPR:$src2, imm1_15:$sh), 0xFFFF)),
2140            (t2PKHTB rGPR:$src1, rGPR:$src2, (asr_shift_imm imm1_15:$sh))>,
2141            Requires<[HasT2ExtractPack]>;
2142
2143//===----------------------------------------------------------------------===//
2144//  Comparison Instructions...
2145//
2146defm t2CMP  : T2I_cmp_irs<0b1101, "cmp",
2147                          BinOpFrag<(ARMcmp node:$LHS, node:$RHS)>>;
2148defm t2CMPz : T2I_cmp_irs<0b1101, "cmp",
2149                          BinOpFrag<(ARMcmpZ node:$LHS, node:$RHS)>>;
2150
2151//FIXME: Disable CMN, as CCodes are backwards from compare expectations
2152//       Compare-to-zero still works out, just not the relationals
2153//defm t2CMN  : T2I_cmp_irs<0b1000, "cmn",
2154//                          BinOpFrag<(ARMcmp node:$LHS,(ineg node:$RHS))>>;
2155defm t2CMNz : T2I_cmp_irs<0b1000, "cmn",
2156                          BinOpFrag<(ARMcmpZ node:$LHS,(ineg node:$RHS))>>;
2157
2158//def : T2Pat<(ARMcmp  GPR:$src, t2_so_imm_neg:$imm),
2159//            (t2CMNri GPR:$src, t2_so_imm_neg:$imm)>;
2160
2161def : T2Pat<(ARMcmpZ  GPR:$src, t2_so_imm_neg:$imm),
2162            (t2CMNzri GPR:$src, t2_so_imm_neg:$imm)>;
2163
2164defm t2TST  : T2I_cmp_irs<0b0000, "tst",
2165                          BinOpFrag<(ARMcmpZ (and node:$LHS, node:$RHS), 0)>>;
2166defm t2TEQ  : T2I_cmp_irs<0b0100, "teq",
2167                          BinOpFrag<(ARMcmpZ (xor node:$LHS, node:$RHS), 0)>>;
2168
2169// Conditional moves
2170// FIXME: should be able to write a pattern for ARMcmov, but can't use
2171// a two-value operand where a dag node expects two operands. :(
2172let neverHasSideEffects = 1 in {
2173def t2MOVCCr : T2I<(outs rGPR:$dst), (ins rGPR:$false, rGPR:$true), IIC_iCMOVr,
2174                   "mov", ".w\t$dst, $true",
2175   [/*(set rGPR:$dst, (ARMcmov rGPR:$false, rGPR:$true, imm:$cc, CCR:$ccr))*/]>,
2176                RegConstraint<"$false = $dst"> {
2177  let Inst{31-27} = 0b11101;
2178  let Inst{26-25} = 0b01;
2179  let Inst{24-21} = 0b0010;
2180  let Inst{20} = 0; // The S bit.
2181  let Inst{19-16} = 0b1111; // Rn
2182  let Inst{14-12} = 0b000;
2183  let Inst{7-4} = 0b0000;
2184}
2185
2186def t2MOVCCi : T2I<(outs rGPR:$dst), (ins rGPR:$false, t2_so_imm:$true),
2187                   IIC_iCMOVi, "mov", ".w\t$dst, $true",
2188[/*(set rGPR:$dst,(ARMcmov rGPR:$false,t2_so_imm:$true, imm:$cc, CCR:$ccr))*/]>,
2189                   RegConstraint<"$false = $dst"> {
2190  let Inst{31-27} = 0b11110;
2191  let Inst{25} = 0;
2192  let Inst{24-21} = 0b0010;
2193  let Inst{20} = 0; // The S bit.
2194  let Inst{19-16} = 0b1111; // Rn
2195  let Inst{15} = 0;
2196}
2197
2198class T2I_movcc_sh<bits<2> opcod, dag oops, dag iops, InstrItinClass itin,
2199                   string opc, string asm, list<dag> pattern>
2200  : T2I<oops, iops, itin, opc, asm, pattern> {
2201  let Inst{31-27} = 0b11101;
2202  let Inst{26-25} = 0b01;
2203  let Inst{24-21} = 0b0010;
2204  let Inst{20} = 0; // The S bit.
2205  let Inst{19-16} = 0b1111; // Rn
2206  let Inst{5-4} = opcod; // Shift type.
2207}
2208def t2MOVCClsl : T2I_movcc_sh<0b00, (outs rGPR:$dst),
2209                             (ins rGPR:$false, rGPR:$true, i32imm:$rhs),
2210                             IIC_iCMOVsi, "lsl", ".w\t$dst, $true, $rhs", []>,
2211                 RegConstraint<"$false = $dst">;
2212def t2MOVCClsr : T2I_movcc_sh<0b01, (outs rGPR:$dst),
2213                             (ins rGPR:$false, rGPR:$true, i32imm:$rhs),
2214                             IIC_iCMOVsi, "lsr", ".w\t$dst, $true, $rhs", []>,
2215                 RegConstraint<"$false = $dst">;
2216def t2MOVCCasr : T2I_movcc_sh<0b10, (outs rGPR:$dst),
2217                             (ins rGPR:$false, rGPR:$true, i32imm:$rhs),
2218                             IIC_iCMOVsi, "asr", ".w\t$dst, $true, $rhs", []>,
2219                 RegConstraint<"$false = $dst">;
2220def t2MOVCCror : T2I_movcc_sh<0b11, (outs rGPR:$dst),
2221                             (ins rGPR:$false, rGPR:$true, i32imm:$rhs),
2222                             IIC_iCMOVsi, "ror", ".w\t$dst, $true, $rhs", []>,
2223                 RegConstraint<"$false = $dst">;
2224} // neverHasSideEffects
2225
2226//===----------------------------------------------------------------------===//
2227// Atomic operations intrinsics
2228//
2229
2230// memory barriers protect the atomic sequences
2231let hasSideEffects = 1 in {
2232def t2DMBsy : AInoP<(outs), (ins), ThumbFrm, NoItinerary, "dmb", "",
2233                    [(ARMMemBarrier)]>, Requires<[IsThumb, HasDB]> {
2234  let Inst{31-4} = 0xF3BF8F5;
2235  // FIXME: add support for options other than a full system DMB
2236  let Inst{3-0} = 0b1111;
2237}
2238
2239def t2DSBsy : AInoP<(outs), (ins), ThumbFrm, NoItinerary, "dsb", "",
2240                    [(ARMSyncBarrier)]>, Requires<[IsThumb, HasDB]> {
2241  let Inst{31-4} = 0xF3BF8F4;
2242  // FIXME: add support for options other than a full system DSB
2243  let Inst{3-0} = 0b1111;
2244}
2245}
2246
2247// Helper class for multiclass T2MemB -- for disassembly only
2248class T2I_memb<string opc, string asm>
2249  : T2I<(outs), (ins), NoItinerary, opc, asm,
2250        [/* For disassembly only; pattern left blank */]>,
2251    Requires<[IsThumb2, HasV7]> {
2252  let Inst{31-20} = 0xf3b;
2253  let Inst{15-14} = 0b10;
2254  let Inst{12} = 0;
2255}
2256
2257multiclass T2MemB<bits<4> op7_4, string opc> {
2258
2259  def st : T2I_memb<opc, "\tst"> {
2260    let Inst{7-4} = op7_4;
2261    let Inst{3-0} = 0b1110;
2262  }
2263
2264  def ish : T2I_memb<opc, "\tish"> {
2265    let Inst{7-4} = op7_4;
2266    let Inst{3-0} = 0b1011;
2267  }
2268
2269  def ishst : T2I_memb<opc, "\tishst"> {
2270    let Inst{7-4} = op7_4;
2271    let Inst{3-0} = 0b1010;
2272  }
2273
2274  def nsh : T2I_memb<opc, "\tnsh"> {
2275    let Inst{7-4} = op7_4;
2276    let Inst{3-0} = 0b0111;
2277  }
2278
2279  def nshst : T2I_memb<opc, "\tnshst"> {
2280    let Inst{7-4} = op7_4;
2281    let Inst{3-0} = 0b0110;
2282  }
2283
2284  def osh : T2I_memb<opc, "\tosh"> {
2285    let Inst{7-4} = op7_4;
2286    let Inst{3-0} = 0b0011;
2287  }
2288
2289  def oshst : T2I_memb<opc, "\toshst"> {
2290    let Inst{7-4} = op7_4;
2291    let Inst{3-0} = 0b0010;
2292  }
2293}
2294
2295// These DMB variants are for disassembly only.
2296defm t2DMB : T2MemB<0b0101, "dmb">;
2297
2298// These DSB variants are for disassembly only.
2299defm t2DSB : T2MemB<0b0100, "dsb">;
2300
2301// ISB has only full system option -- for disassembly only
2302def t2ISBsy : T2I_memb<"isb", ""> {
2303  let Inst{7-4} = 0b0110;
2304  let Inst{3-0} = 0b1111;
2305}
2306
2307class T2I_ldrex<bits<2> opcod, dag oops, dag iops, AddrMode am, SizeFlagVal sz,
2308                InstrItinClass itin, string opc, string asm, string cstr,
2309                list<dag> pattern, bits<4> rt2 = 0b1111>
2310  : Thumb2I<oops, iops, am, sz, itin, opc, asm, cstr, pattern> {
2311  let Inst{31-27} = 0b11101;
2312  let Inst{26-20} = 0b0001101;
2313  let Inst{11-8} = rt2;
2314  let Inst{7-6} = 0b01;
2315  let Inst{5-4} = opcod;
2316  let Inst{3-0} = 0b1111;
2317}
2318class T2I_strex<bits<2> opcod, dag oops, dag iops, AddrMode am, SizeFlagVal sz,
2319                InstrItinClass itin, string opc, string asm, string cstr,
2320                list<dag> pattern, bits<4> rt2 = 0b1111>
2321  : Thumb2I<oops, iops, am, sz, itin, opc, asm, cstr, pattern> {
2322  let Inst{31-27} = 0b11101;
2323  let Inst{26-20} = 0b0001100;
2324  let Inst{11-8} = rt2;
2325  let Inst{7-6} = 0b01;
2326  let Inst{5-4} = opcod;
2327}
2328
2329let mayLoad = 1 in {
2330def t2LDREXB : T2I_ldrex<0b00, (outs rGPR:$dest), (ins rGPR:$ptr), AddrModeNone,
2331                         Size4Bytes, NoItinerary, "ldrexb", "\t$dest, [$ptr]",
2332                         "", []>;
2333def t2LDREXH : T2I_ldrex<0b01, (outs rGPR:$dest), (ins rGPR:$ptr), AddrModeNone,
2334                         Size4Bytes, NoItinerary, "ldrexh", "\t$dest, [$ptr]",
2335                         "", []>;
2336def t2LDREX  : Thumb2I<(outs rGPR:$dest), (ins rGPR:$ptr), AddrModeNone,
2337                       Size4Bytes, NoItinerary,
2338                       "ldrex", "\t$dest, [$ptr]", "",
2339                      []> {
2340  let Inst{31-27} = 0b11101;
2341  let Inst{26-20} = 0b0000101;
2342  let Inst{11-8} = 0b1111;
2343  let Inst{7-0} = 0b00000000; // imm8 = 0
2344}
2345def t2LDREXD : T2I_ldrex<0b11, (outs rGPR:$dest, rGPR:$dest2), (ins rGPR:$ptr),
2346                         AddrModeNone, Size4Bytes, NoItinerary,
2347                         "ldrexd", "\t$dest, $dest2, [$ptr]", "",
2348                         [], {?, ?, ?, ?}>;
2349}
2350
2351let mayStore = 1, Constraints = "@earlyclobber $success" in {
2352def t2STREXB : T2I_strex<0b00, (outs rGPR:$success), (ins rGPR:$src, rGPR:$ptr),
2353                         AddrModeNone, Size4Bytes, NoItinerary,
2354                         "strexb", "\t$success, $src, [$ptr]", "", []>;
2355def t2STREXH : T2I_strex<0b01, (outs rGPR:$success), (ins rGPR:$src, rGPR:$ptr),
2356                         AddrModeNone, Size4Bytes, NoItinerary,
2357                         "strexh", "\t$success, $src, [$ptr]", "", []>;
2358def t2STREX  : Thumb2I<(outs rGPR:$success), (ins rGPR:$src, rGPR:$ptr),
2359                       AddrModeNone, Size4Bytes, NoItinerary,
2360                       "strex", "\t$success, $src, [$ptr]", "",
2361                      []> {
2362  let Inst{31-27} = 0b11101;
2363  let Inst{26-20} = 0b0000100;
2364  let Inst{7-0} = 0b00000000; // imm8 = 0
2365}
2366def t2STREXD : T2I_strex<0b11, (outs rGPR:$success),
2367                         (ins rGPR:$src, rGPR:$src2, rGPR:$ptr),
2368                         AddrModeNone, Size4Bytes, NoItinerary,
2369                         "strexd", "\t$success, $src, $src2, [$ptr]", "", [],
2370                         {?, ?, ?, ?}>;
2371}
2372
2373// Clear-Exclusive is for disassembly only.
2374def t2CLREX : T2I<(outs), (ins), NoItinerary, "clrex", "",
2375                  [/* For disassembly only; pattern left blank */]>,
2376            Requires<[IsARM, HasV7]>  {
2377  let Inst{31-20} = 0xf3b;
2378  let Inst{15-14} = 0b10;
2379  let Inst{12} = 0;
2380  let Inst{7-4} = 0b0010;
2381}
2382
2383//===----------------------------------------------------------------------===//
2384// TLS Instructions
2385//
2386
2387// __aeabi_read_tp preserves the registers r1-r3.
2388let isCall = 1,
2389  Defs = [R0, R12, LR, CPSR] in {
2390  def t2TPsoft : T2XI<(outs), (ins), IIC_Br,
2391                     "bl\t__aeabi_read_tp",
2392                     [(set R0, ARMthread_pointer)]> {
2393    let Inst{31-27} = 0b11110;
2394    let Inst{15-14} = 0b11;
2395    let Inst{12} = 1;
2396  }
2397}
2398
2399//===----------------------------------------------------------------------===//
2400// SJLJ Exception handling intrinsics
2401//   eh_sjlj_setjmp() is an instruction sequence to store the return
2402//   address and save #0 in R0 for the non-longjmp case.
2403//   Since by its nature we may be coming from some other function to get
2404//   here, and we're using the stack frame for the containing function to
2405//   save/restore registers, we can't keep anything live in regs across
2406//   the eh_sjlj_setjmp(), else it will almost certainly have been tromped upon
2407//   when we get here from a longjmp(). We force everthing out of registers
2408//   except for our own input by listing the relevant registers in Defs. By
2409//   doing so, we also cause the prologue/epilogue code to actively preserve
2410//   all of the callee-saved resgisters, which is exactly what we want.
2411//   $val is a scratch register for our use.
2412let Defs =
2413  [ R0,  R1,  R2,  R3,  R4,  R5,  R6,  R7,  R8,  R9,  R10, R11, R12, LR,  D0,
2414    D1,  D2,  D3,  D4,  D5,  D6,  D7,  D8,  D9,  D10, D11, D12, D13, D14, D15,
2415    D16, D17, D18, D19, D20, D21, D22, D23, D24, D25, D26, D27, D28, D29, D30,
2416    D31 ], hasSideEffects = 1, isBarrier = 1 in {
2417  def t2Int_eh_sjlj_setjmp : Thumb2XI<(outs), (ins tGPR:$src, tGPR:$val),
2418                               AddrModeNone, SizeSpecial, NoItinerary,
2419                               "mov\t$val, pc\t${:comment} begin eh.setjmp\n\t"
2420                               "adds\t$val, #7\n\t"
2421                               "str\t$val, [$src, #4]\n\t"
2422                               "movs\tr0, #0\n\t"
2423                               "b\t1f\n\t"
2424                               "movs\tr0, #1\t${:comment} end eh.setjmp\n\t"
2425                               "1:", "",
2426                          [(set R0, (ARMeh_sjlj_setjmp tGPR:$src, tGPR:$val))]>,
2427                             Requires<[IsThumb2, HasVFP2]>;
2428}
2429
2430let Defs =
2431  [ R0,  R1,  R2,  R3,  R4,  R5,  R6,  R7,  R8,  R9,  R10, R11, R12, LR ],
2432  hasSideEffects = 1, isBarrier = 1 in {
2433  def t2Int_eh_sjlj_setjmp_nofp : Thumb2XI<(outs), (ins tGPR:$src, tGPR:$val),
2434                               AddrModeNone, SizeSpecial, NoItinerary,
2435                               "mov\t$val, pc\t${:comment} begin eh.setjmp\n\t"
2436                               "adds\t$val, #7\n\t"
2437                               "str\t$val, [$src, #4]\n\t"
2438                               "movs\tr0, #0\n\t"
2439                               "b\t1f\n\t"
2440                               "movs\tr0, #1\t${:comment} end eh.setjmp\n\t"
2441                               "1:", "",
2442                          [(set R0, (ARMeh_sjlj_setjmp tGPR:$src, tGPR:$val))]>,
2443                                  Requires<[IsThumb2, NoVFP]>;
2444}
2445
2446
2447//===----------------------------------------------------------------------===//
2448// Control-Flow Instructions
2449//
2450
2451// FIXME: remove when we have a way to marking a MI with these properties.
2452// FIXME: $dst1 should be a def. But the extra ops must be in the end of the
2453// operand list.
2454// FIXME: Should pc be an implicit operand like PICADD, etc?
2455let isReturn = 1, isTerminator = 1, isBarrier = 1, mayLoad = 1,
2456    hasExtraDefRegAllocReq = 1 in
2457  def t2LDM_RET : T2XIt<(outs GPR:$wb), (ins addrmode4:$addr, pred:$p,
2458                                         reglist:$dsts, variable_ops), IIC_Br,
2459                        "ldm${addr:submode}${p}${addr:wide}\t$addr!, $dsts",
2460                        "$addr.addr = $wb", []> {
2461  let Inst{31-27} = 0b11101;
2462  let Inst{26-25} = 0b00;
2463  let Inst{24-23} = {?, ?}; // IA: '01', DB: '10'
2464  let Inst{22} = 0;
2465  let Inst{21} = 1; // The W bit.
2466  let Inst{20} = 1; // Load
2467}
2468
2469let isBranch = 1, isTerminator = 1, isBarrier = 1 in {
2470let isPredicable = 1 in
2471def t2B   : T2XI<(outs), (ins brtarget:$target), IIC_Br,
2472                 "b.w\t$target",
2473                 [(br bb:$target)]> {
2474  let Inst{31-27} = 0b11110;
2475  let Inst{15-14} = 0b10;
2476  let Inst{12} = 1;
2477}
2478
2479let isNotDuplicable = 1, isIndirectBranch = 1 in {
2480def t2BR_JT :
2481    T2JTI<(outs),
2482          (ins GPR:$target, GPR:$index, jt2block_operand:$jt, i32imm:$id),
2483           IIC_Br, "mov\tpc, $target$jt",
2484          [(ARMbr2jt GPR:$target, GPR:$index, tjumptable:$jt, imm:$id)]> {
2485  let Inst{31-27} = 0b11101;
2486  let Inst{26-20} = 0b0100100;
2487  let Inst{19-16} = 0b1111;
2488  let Inst{14-12} = 0b000;
2489  let Inst{11-8} = 0b1111; // Rd = pc
2490  let Inst{7-4} = 0b0000;
2491}
2492
2493// FIXME: Add a non-pc based case that can be predicated.
2494def t2TBB :
2495    T2JTI<(outs),
2496        (ins tb_addrmode:$index, jt2block_operand:$jt, i32imm:$id),
2497         IIC_Br, "tbb\t$index$jt", []> {
2498  let Inst{31-27} = 0b11101;
2499  let Inst{26-20} = 0b0001101;
2500  let Inst{19-16} = 0b1111; // Rn = pc (table follows this instruction)
2501  let Inst{15-8} = 0b11110000;
2502  let Inst{7-4} = 0b0000; // B form
2503}
2504
2505def t2TBH :
2506    T2JTI<(outs),
2507        (ins tb_addrmode:$index, jt2block_operand:$jt, i32imm:$id),
2508         IIC_Br, "tbh\t$index$jt", []> {
2509  let Inst{31-27} = 0b11101;
2510  let Inst{26-20} = 0b0001101;
2511  let Inst{19-16} = 0b1111; // Rn = pc (table follows this instruction)
2512  let Inst{15-8} = 0b11110000;
2513  let Inst{7-4} = 0b0001; // H form
2514}
2515
2516// Generic versions of the above two instructions, for disassembly only
2517
2518def t2TBBgen : T2I<(outs), (ins GPR:$a, GPR:$b), IIC_Br,
2519                    "tbb", "\t[$a, $b]", []>{
2520  let Inst{31-27} = 0b11101;
2521  let Inst{26-20} = 0b0001101;
2522  let Inst{15-8} = 0b11110000;
2523  let Inst{7-4} = 0b0000; // B form
2524}
2525
2526def t2TBHgen : T2I<(outs), (ins GPR:$a, GPR:$b), IIC_Br,
2527                   "tbh", "\t[$a, $b, lsl #1]", []> {
2528  let Inst{31-27} = 0b11101;
2529  let Inst{26-20} = 0b0001101;
2530  let Inst{15-8} = 0b11110000;
2531  let Inst{7-4} = 0b0001; // H form
2532}
2533} // isNotDuplicable, isIndirectBranch
2534
2535} // isBranch, isTerminator, isBarrier
2536
2537// FIXME: should be able to write a pattern for ARMBrcond, but can't use
2538// a two-value operand where a dag node expects two operands. :(
2539let isBranch = 1, isTerminator = 1 in
2540def t2Bcc : T2I<(outs), (ins brtarget:$target), IIC_Br,
2541                "b", ".w\t$target",
2542                [/*(ARMbrcond bb:$target, imm:$cc)*/]> {
2543  let Inst{31-27} = 0b11110;
2544  let Inst{15-14} = 0b10;
2545  let Inst{12} = 0;
2546}
2547
2548
2549// IT block
2550let Defs = [ITSTATE] in
2551def t2IT : Thumb2XI<(outs), (ins it_pred:$cc, it_mask:$mask),
2552                    AddrModeNone, Size2Bytes,  IIC_iALUx,
2553                    "it$mask\t$cc", "", []> {
2554  // 16-bit instruction.
2555  let Inst{31-16} = 0x0000;
2556  let Inst{15-8} = 0b10111111;
2557}
2558
2559// Branch and Exchange Jazelle -- for disassembly only
2560// Rm = Inst{19-16}
2561def t2BXJ : T2I<(outs), (ins rGPR:$func), NoItinerary, "bxj", "\t$func",
2562              [/* For disassembly only; pattern left blank */]> {
2563  let Inst{31-27} = 0b11110;
2564  let Inst{26} = 0;
2565  let Inst{25-20} = 0b111100;
2566  let Inst{15-14} = 0b10;
2567  let Inst{12} = 0;
2568}
2569
2570// Change Processor State is a system instruction -- for disassembly only.
2571// The singleton $opt operand contains the following information:
2572// opt{4-0} = mode from Inst{4-0}
2573// opt{5} = changemode from Inst{17}
2574// opt{8-6} = AIF from Inst{8-6}
2575// opt{10-9} = imod from Inst{19-18} with 0b10 as enable and 0b11 as disable
2576def t2CPS : T2XI<(outs),(ins cps_opt:$opt), NoItinerary, "cps$opt",
2577                 [/* For disassembly only; pattern left blank */]> {
2578  let Inst{31-27} = 0b11110;
2579  let Inst{26} = 0;
2580  let Inst{25-20} = 0b111010;
2581  let Inst{15-14} = 0b10;
2582  let Inst{12} = 0;
2583}
2584
2585// A6.3.4 Branches and miscellaneous control
2586// Table A6-14 Change Processor State, and hint instructions
2587// Helper class for disassembly only.
2588class T2I_hint<bits<8> op7_0, string opc, string asm>
2589  : T2I<(outs), (ins), NoItinerary, opc, asm,
2590        [/* For disassembly only; pattern left blank */]> {
2591  let Inst{31-20} = 0xf3a;
2592  let Inst{15-14} = 0b10;
2593  let Inst{12} = 0;
2594  let Inst{10-8} = 0b000;
2595  let Inst{7-0} = op7_0;
2596}
2597
2598def t2NOP   : T2I_hint<0b00000000, "nop",   ".w">;
2599def t2YIELD : T2I_hint<0b00000001, "yield", ".w">;
2600def t2WFE   : T2I_hint<0b00000010, "wfe",   ".w">;
2601def t2WFI   : T2I_hint<0b00000011, "wfi",   ".w">;
2602def t2SEV   : T2I_hint<0b00000100, "sev",   ".w">;
2603
2604def t2DBG : T2I<(outs),(ins i32imm:$opt), NoItinerary, "dbg", "\t$opt",
2605                [/* For disassembly only; pattern left blank */]> {
2606  let Inst{31-20} = 0xf3a;
2607  let Inst{15-14} = 0b10;
2608  let Inst{12} = 0;
2609  let Inst{10-8} = 0b000;
2610  let Inst{7-4} = 0b1111;
2611}
2612
2613// Secure Monitor Call is a system instruction -- for disassembly only
2614// Option = Inst{19-16}
2615def t2SMC : T2I<(outs), (ins i32imm:$opt), NoItinerary, "smc", "\t$opt",
2616                [/* For disassembly only; pattern left blank */]> {
2617  let Inst{31-27} = 0b11110;
2618  let Inst{26-20} = 0b1111111;
2619  let Inst{15-12} = 0b1000;
2620}
2621
2622// Store Return State is a system instruction -- for disassembly only
2623def t2SRSDBW : T2I<(outs),(ins i32imm:$mode),NoItinerary,"srsdb","\tsp!, $mode",
2624                   [/* For disassembly only; pattern left blank */]> {
2625  let Inst{31-27} = 0b11101;
2626  let Inst{26-20} = 0b0000010; // W = 1
2627}
2628
2629def t2SRSDB  : T2I<(outs),(ins i32imm:$mode),NoItinerary,"srsdb","\tsp, $mode",
2630                   [/* For disassembly only; pattern left blank */]> {
2631  let Inst{31-27} = 0b11101;
2632  let Inst{26-20} = 0b0000000; // W = 0
2633}
2634
2635def t2SRSIAW : T2I<(outs),(ins i32imm:$mode),NoItinerary,"srsia","\tsp!, $mode",
2636                   [/* For disassembly only; pattern left blank */]> {
2637  let Inst{31-27} = 0b11101;
2638  let Inst{26-20} = 0b0011010; // W = 1
2639}
2640
2641def t2SRSIA  : T2I<(outs), (ins i32imm:$mode),NoItinerary,"srsia","\tsp, $mode",
2642                   [/* For disassembly only; pattern left blank */]> {
2643  let Inst{31-27} = 0b11101;
2644  let Inst{26-20} = 0b0011000; // W = 0
2645}
2646
2647// Return From Exception is a system instruction -- for disassembly only
2648def t2RFEDBW : T2I<(outs), (ins rGPR:$base), NoItinerary, "rfedb", "\t$base!",
2649                   [/* For disassembly only; pattern left blank */]> {
2650  let Inst{31-27} = 0b11101;
2651  let Inst{26-20} = 0b0000011; // W = 1
2652}
2653
2654def t2RFEDB  : T2I<(outs), (ins rGPR:$base), NoItinerary, "rfeab", "\t$base",
2655                   [/* For disassembly only; pattern left blank */]> {
2656  let Inst{31-27} = 0b11101;
2657  let Inst{26-20} = 0b0000001; // W = 0
2658}
2659
2660def t2RFEIAW : T2I<(outs), (ins rGPR:$base), NoItinerary, "rfeia", "\t$base!",
2661                   [/* For disassembly only; pattern left blank */]> {
2662  let Inst{31-27} = 0b11101;
2663  let Inst{26-20} = 0b0011011; // W = 1
2664}
2665
2666def t2RFEIA  : T2I<(outs), (ins rGPR:$base), NoItinerary, "rfeia", "\t$base",
2667                   [/* For disassembly only; pattern left blank */]> {
2668  let Inst{31-27} = 0b11101;
2669  let Inst{26-20} = 0b0011001; // W = 0
2670}
2671
2672//===----------------------------------------------------------------------===//
2673// Non-Instruction Patterns
2674//
2675
2676// Two piece so_imms.
2677def : T2Pat<(or rGPR:$LHS, t2_so_imm2part:$RHS),
2678             (t2ORRri (t2ORRri rGPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
2679                    (t2_so_imm2part_2 imm:$RHS))>;
2680def : T2Pat<(xor rGPR:$LHS, t2_so_imm2part:$RHS),
2681             (t2EORri (t2EORri rGPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
2682                    (t2_so_imm2part_2 imm:$RHS))>;
2683def : T2Pat<(add rGPR:$LHS, t2_so_imm2part:$RHS),
2684             (t2ADDri (t2ADDri rGPR:$LHS, (t2_so_imm2part_1 imm:$RHS)),
2685                    (t2_so_imm2part_2 imm:$RHS))>;
2686def : T2Pat<(add rGPR:$LHS, t2_so_neg_imm2part:$RHS),
2687             (t2SUBri (t2SUBri rGPR:$LHS, (t2_so_neg_imm2part_1 imm:$RHS)),
2688                    (t2_so_neg_imm2part_2 imm:$RHS))>;
2689
2690// 32-bit immediate using movw + movt.
2691// This is a single pseudo instruction to make it re-materializable. Remove
2692// when we can do generalized remat.
2693let isReMaterializable = 1 in
2694def t2MOVi32imm : T2Ix2<(outs rGPR:$dst), (ins i32imm:$src), IIC_iMOVi,
2695                   "movw", "\t$dst, ${src:lo16}\n\tmovt${p}\t$dst, ${src:hi16}",
2696                     [(set rGPR:$dst, (i32 imm:$src))]>;
2697
2698// ConstantPool, GlobalAddress, and JumpTable
2699def : T2Pat<(ARMWrapper  tglobaladdr :$dst), (t2LEApcrel tglobaladdr :$dst)>,
2700           Requires<[IsThumb2, DontUseMovt]>;
2701def : T2Pat<(ARMWrapper  tconstpool  :$dst), (t2LEApcrel tconstpool  :$dst)>;
2702def : T2Pat<(ARMWrapper  tglobaladdr :$dst), (t2MOVi32imm tglobaladdr :$dst)>,
2703           Requires<[IsThumb2, UseMovt]>;
2704
2705def : T2Pat<(ARMWrapperJT tjumptable:$dst, imm:$id),
2706            (t2LEApcrelJT tjumptable:$dst, imm:$id)>;
2707
2708// Pseudo instruction that combines ldr from constpool and add pc. This should
2709// be expanded into two instructions late to allow if-conversion and
2710// scheduling.
2711let canFoldAsLoad = 1, isReMaterializable = 1 in
2712def t2LDRpci_pic : PseudoInst<(outs GPR:$dst), (ins i32imm:$addr, pclabel:$cp),
2713                   NoItinerary,
2714                   "${:comment} ldr.w\t$dst, $addr\n$cp:\n\tadd\t$dst, pc",
2715               [(set GPR:$dst, (ARMpic_add (load (ARMWrapper tconstpool:$addr)),
2716                                           imm:$cp))]>,
2717               Requires<[IsThumb2]>;
2718
2719//===----------------------------------------------------------------------===//
2720// Move between special register and ARM core register -- for disassembly only
2721//
2722
2723// Rd = Instr{11-8}
2724def t2MRS : T2I<(outs rGPR:$dst), (ins), NoItinerary, "mrs", "\t$dst, cpsr",
2725                [/* For disassembly only; pattern left blank */]> {
2726  let Inst{31-27} = 0b11110;
2727  let Inst{26} = 0;
2728  let Inst{25-21} = 0b11111;
2729  let Inst{20} = 0; // The R bit.
2730  let Inst{15-14} = 0b10;
2731  let Inst{12} = 0;
2732}
2733
2734// Rd = Instr{11-8}
2735def t2MRSsys : T2I<(outs rGPR:$dst), (ins), NoItinerary, "mrs", "\t$dst, spsr",
2736                   [/* For disassembly only; pattern left blank */]> {
2737  let Inst{31-27} = 0b11110;
2738  let Inst{26} = 0;
2739  let Inst{25-21} = 0b11111;
2740  let Inst{20} = 1; // The R bit.
2741  let Inst{15-14} = 0b10;
2742  let Inst{12} = 0;
2743}
2744
2745// Rn = Inst{19-16}
2746def t2MSR : T2I<(outs), (ins rGPR:$src, msr_mask:$mask), NoItinerary, "msr",
2747                "\tcpsr$mask, $src",
2748                [/* For disassembly only; pattern left blank */]> {
2749  let Inst{31-27} = 0b11110;
2750  let Inst{26} = 0;
2751  let Inst{25-21} = 0b11100;
2752  let Inst{20} = 0; // The R bit.
2753  let Inst{15-14} = 0b10;
2754  let Inst{12} = 0;
2755}
2756
2757// Rn = Inst{19-16}
2758def t2MSRsys : T2I<(outs), (ins rGPR:$src, msr_mask:$mask), NoItinerary, "msr",
2759                   "\tspsr$mask, $src",
2760                   [/* For disassembly only; pattern left blank */]> {
2761  let Inst{31-27} = 0b11110;
2762  let Inst{26} = 0;
2763  let Inst{25-21} = 0b11100;
2764  let Inst{20} = 1; // The R bit.
2765  let Inst{15-14} = 0b10;
2766  let Inst{12} = 0;
2767}
2768