Patch by David Conrad:
[oota-llvm.git] / lib / Target / ARM / ARMInstrInfo.td
1 //===- ARMInstrInfo.td - Target Description for ARM Target -*- tablegen -*-===//
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 ARM instructions in TableGen format.
11 //
12 //===----------------------------------------------------------------------===//
13
14 //===----------------------------------------------------------------------===//
15 // ARM specific DAG Nodes.
16 //
17
18 // Type profiles.
19 def SDT_ARMCallSeqStart : SDCallSeqStart<[ SDTCisVT<0, i32> ]>;
20 def SDT_ARMCallSeqEnd   : SDCallSeqEnd<[ SDTCisVT<0, i32>, SDTCisVT<1, i32> ]>;
21
22 def SDT_ARMSaveCallPC : SDTypeProfile<0, 1, []>;
23
24 def SDT_ARMcall    : SDTypeProfile<0, -1, [SDTCisInt<0>]>;
25
26 def SDT_ARMCMov    : SDTypeProfile<1, 3,
27                                    [SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>,
28                                     SDTCisVT<3, i32>]>;
29
30 def SDT_ARMBrcond  : SDTypeProfile<0, 2,
31                                    [SDTCisVT<0, OtherVT>, SDTCisVT<1, i32>]>;
32
33 def SDT_ARMBrJT    : SDTypeProfile<0, 3,
34                                   [SDTCisPtrTy<0>, SDTCisVT<1, i32>,
35                                    SDTCisVT<2, i32>]>;
36
37 def SDT_ARMBr2JT   : SDTypeProfile<0, 4,
38                                   [SDTCisPtrTy<0>, SDTCisVT<1, i32>,
39                                    SDTCisVT<2, i32>, SDTCisVT<3, i32>]>;
40
41 def SDT_ARMCmp     : SDTypeProfile<0, 2, [SDTCisSameAs<0, 1>]>;
42
43 def SDT_ARMPICAdd  : SDTypeProfile<1, 2, [SDTCisSameAs<0, 1>,
44                                           SDTCisPtrTy<1>, SDTCisVT<2, i32>]>;
45
46 def SDT_ARMThreadPointer : SDTypeProfile<1, 0, [SDTCisPtrTy<0>]>;
47 def SDT_ARMEH_SJLJ_Setjmp : SDTypeProfile<1, 1, [SDTCisInt<0>, SDTCisPtrTy<1>]>;
48
49 def SDT_ARMMEMBARRIERV7  : SDTypeProfile<0, 0, []>;
50 def SDT_ARMSYNCBARRIERV7 : SDTypeProfile<0, 0, []>;
51 def SDT_ARMMEMBARRIERV6  : SDTypeProfile<0, 1, [SDTCisInt<0>]>;
52 def SDT_ARMSYNCBARRIERV6 : SDTypeProfile<0, 1, [SDTCisInt<0>]>;
53
54 // Node definitions.
55 def ARMWrapper       : SDNode<"ARMISD::Wrapper",     SDTIntUnaryOp>;
56 def ARMWrapperJT     : SDNode<"ARMISD::WrapperJT",   SDTIntBinOp>;
57
58 def ARMcallseq_start : SDNode<"ISD::CALLSEQ_START", SDT_ARMCallSeqStart,
59                               [SDNPHasChain, SDNPOutFlag]>;
60 def ARMcallseq_end   : SDNode<"ISD::CALLSEQ_END",   SDT_ARMCallSeqEnd,
61                               [SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>;
62
63 def ARMcall          : SDNode<"ARMISD::CALL", SDT_ARMcall,
64                               [SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>;
65 def ARMcall_pred    : SDNode<"ARMISD::CALL_PRED", SDT_ARMcall,
66                               [SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>;
67 def ARMcall_nolink   : SDNode<"ARMISD::CALL_NOLINK", SDT_ARMcall,
68                               [SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>;
69
70 def ARMretflag       : SDNode<"ARMISD::RET_FLAG", SDTNone,
71                               [SDNPHasChain, SDNPOptInFlag]>;
72
73 def ARMcmov          : SDNode<"ARMISD::CMOV", SDT_ARMCMov,
74                               [SDNPInFlag]>;
75 def ARMcneg          : SDNode<"ARMISD::CNEG", SDT_ARMCMov,
76                               [SDNPInFlag]>;
77
78 def ARMbrcond        : SDNode<"ARMISD::BRCOND", SDT_ARMBrcond,
79                               [SDNPHasChain, SDNPInFlag, SDNPOutFlag]>;
80
81 def ARMbrjt          : SDNode<"ARMISD::BR_JT", SDT_ARMBrJT,
82                               [SDNPHasChain]>;
83 def ARMbr2jt         : SDNode<"ARMISD::BR2_JT", SDT_ARMBr2JT,
84                               [SDNPHasChain]>;
85
86 def ARMcmp           : SDNode<"ARMISD::CMP", SDT_ARMCmp,
87                               [SDNPOutFlag]>;
88
89 def ARMcmpZ          : SDNode<"ARMISD::CMPZ", SDT_ARMCmp,
90                               [SDNPOutFlag,SDNPCommutative]>;
91
92 def ARMpic_add       : SDNode<"ARMISD::PIC_ADD", SDT_ARMPICAdd>;
93
94 def ARMsrl_flag      : SDNode<"ARMISD::SRL_FLAG", SDTIntUnaryOp, [SDNPOutFlag]>;
95 def ARMsra_flag      : SDNode<"ARMISD::SRA_FLAG", SDTIntUnaryOp, [SDNPOutFlag]>;
96 def ARMrrx           : SDNode<"ARMISD::RRX"     , SDTIntUnaryOp, [SDNPInFlag ]>;
97
98 def ARMthread_pointer: SDNode<"ARMISD::THREAD_POINTER", SDT_ARMThreadPointer>;
99 def ARMeh_sjlj_setjmp: SDNode<"ARMISD::EH_SJLJ_SETJMP", SDT_ARMEH_SJLJ_Setjmp>;
100
101 def ARMMemBarrierV7  : SDNode<"ARMISD::MEMBARRIER", SDT_ARMMEMBARRIERV7,
102                               [SDNPHasChain]>;
103 def ARMSyncBarrierV7 : SDNode<"ARMISD::SYNCBARRIER", SDT_ARMMEMBARRIERV7,
104                               [SDNPHasChain]>;
105 def ARMMemBarrierV6  : SDNode<"ARMISD::MEMBARRIER", SDT_ARMMEMBARRIERV6,
106                               [SDNPHasChain]>;
107 def ARMSyncBarrierV6 : SDNode<"ARMISD::SYNCBARRIER", SDT_ARMMEMBARRIERV6,
108                               [SDNPHasChain]>;
109
110 //===----------------------------------------------------------------------===//
111 // ARM Instruction Predicate Definitions.
112 //
113 def HasV5T    : Predicate<"Subtarget->hasV5TOps()">;
114 def HasV5TE   : Predicate<"Subtarget->hasV5TEOps()">;
115 def HasV6     : Predicate<"Subtarget->hasV6Ops()">;
116 def HasV6T2   : Predicate<"Subtarget->hasV6T2Ops()">;
117 def NoV6T2    : Predicate<"!Subtarget->hasV6T2Ops()">;
118 def HasV7     : Predicate<"Subtarget->hasV7Ops()">;
119 def HasVFP2   : Predicate<"Subtarget->hasVFP2()">;
120 def HasVFP3   : Predicate<"Subtarget->hasVFP3()">;
121 def HasNEON   : Predicate<"Subtarget->hasNEON()">;
122 def UseNEONForFP : Predicate<"Subtarget->useNEONForSinglePrecisionFP()">;
123 def DontUseNEONForFP : Predicate<"!Subtarget->useNEONForSinglePrecisionFP()">;
124 def IsThumb   : Predicate<"Subtarget->isThumb()">;
125 def IsThumb1Only : Predicate<"Subtarget->isThumb1Only()">;
126 def IsThumb2  : Predicate<"Subtarget->isThumb2()">;
127 def IsARM     : Predicate<"!Subtarget->isThumb()">;
128 def IsDarwin    : Predicate<"Subtarget->isTargetDarwin()">;
129 def IsNotDarwin : Predicate<"!Subtarget->isTargetDarwin()">;
130 def CarryDefIsUnused : Predicate<"!N->hasAnyUseOfValue(1)">;
131 def CarryDefIsUsed   : Predicate<"N->hasAnyUseOfValue(1)">;
132
133 // FIXME: Eventually this will be just "hasV6T2Ops".
134 def UseMovt   : Predicate<"Subtarget->useMovt()">;
135 def DontUseMovt : Predicate<"!Subtarget->useMovt()">;
136
137 //===----------------------------------------------------------------------===//
138 // ARM Flag Definitions.
139
140 class RegConstraint<string C> {
141   string Constraints = C;
142 }
143
144 //===----------------------------------------------------------------------===//
145 //  ARM specific transformation functions and pattern fragments.
146 //
147
148 // so_imm_neg_XFORM - Return a so_imm value packed into the format described for
149 // so_imm_neg def below.
150 def so_imm_neg_XFORM : SDNodeXForm<imm, [{
151   return CurDAG->getTargetConstant(-(int)N->getZExtValue(), MVT::i32);
152 }]>;
153
154 // so_imm_not_XFORM - Return a so_imm value packed into the format described for
155 // so_imm_not def below.
156 def so_imm_not_XFORM : SDNodeXForm<imm, [{
157   return CurDAG->getTargetConstant(~(int)N->getZExtValue(), MVT::i32);
158 }]>;
159
160 // rot_imm predicate - True if the 32-bit immediate is equal to 8, 16, or 24.
161 def rot_imm : PatLeaf<(i32 imm), [{
162   int32_t v = (int32_t)N->getZExtValue();
163   return v == 8 || v == 16 || v == 24;
164 }]>;
165
166 /// imm1_15 predicate - True if the 32-bit immediate is in the range [1,15].
167 def imm1_15 : PatLeaf<(i32 imm), [{
168   return (int32_t)N->getZExtValue() >= 1 && (int32_t)N->getZExtValue() < 16;
169 }]>;
170
171 /// imm16_31 predicate - True if the 32-bit immediate is in the range [16,31].
172 def imm16_31 : PatLeaf<(i32 imm), [{
173   return (int32_t)N->getZExtValue() >= 16 && (int32_t)N->getZExtValue() < 32;
174 }]>;
175
176 def so_imm_neg : 
177   PatLeaf<(imm), [{
178     return ARM_AM::getSOImmVal(-(int)N->getZExtValue()) != -1;
179   }], so_imm_neg_XFORM>;
180
181 def so_imm_not :
182   PatLeaf<(imm), [{
183     return ARM_AM::getSOImmVal(~(int)N->getZExtValue()) != -1;
184   }], so_imm_not_XFORM>;
185
186 // sext_16_node predicate - True if the SDNode is sign-extended 16 or more bits.
187 def sext_16_node : PatLeaf<(i32 GPR:$a), [{
188   return CurDAG->ComputeNumSignBits(SDValue(N,0)) >= 17;
189 }]>;
190
191 /// bf_inv_mask_imm predicate - An AND mask to clear an arbitrary width bitfield
192 /// e.g., 0xf000ffff
193 def bf_inv_mask_imm : Operand<i32>,
194                       PatLeaf<(imm), [{ 
195   uint32_t v = (uint32_t)N->getZExtValue();
196   if (v == 0xffffffff)
197     return 0;
198   // there can be 1's on either or both "outsides", all the "inside"
199   // bits must be 0's
200   unsigned int lsb = 0, msb = 31;
201   while (v & (1 << msb)) --msb;
202   while (v & (1 << lsb)) ++lsb;
203   for (unsigned int i = lsb; i <= msb; ++i) {
204     if (v & (1 << i))
205       return 0;
206   }
207   return 1;
208 }] > {
209   let PrintMethod = "printBitfieldInvMaskImmOperand";
210 }
211
212 /// Split a 32-bit immediate into two 16 bit parts.
213 def lo16 : SDNodeXForm<imm, [{
214   return CurDAG->getTargetConstant((uint32_t)N->getZExtValue() & 0xffff,
215                                    MVT::i32);
216 }]>;
217
218 def hi16 : SDNodeXForm<imm, [{
219   return CurDAG->getTargetConstant((uint32_t)N->getZExtValue() >> 16, MVT::i32);
220 }]>;
221
222 def lo16AllZero : PatLeaf<(i32 imm), [{
223   // Returns true if all low 16-bits are 0.
224   return (((uint32_t)N->getZExtValue()) & 0xFFFFUL) == 0;
225 }], hi16>;
226
227 /// imm0_65535 predicate - True if the 32-bit immediate is in the range 
228 /// [0.65535].
229 def imm0_65535 : PatLeaf<(i32 imm), [{
230   return (uint32_t)N->getZExtValue() < 65536;
231 }]>;
232
233 class BinOpFrag<dag res> : PatFrag<(ops node:$LHS, node:$RHS), res>;
234 class UnOpFrag <dag res> : PatFrag<(ops node:$Src), res>;
235
236 //===----------------------------------------------------------------------===//
237 // Operand Definitions.
238 //
239
240 // Branch target.
241 def brtarget : Operand<OtherVT>;
242
243 // A list of registers separated by comma. Used by load/store multiple.
244 def reglist : Operand<i32> {
245   let PrintMethod = "printRegisterList";
246 }
247
248 // An operand for the CONSTPOOL_ENTRY pseudo-instruction.
249 def cpinst_operand : Operand<i32> {
250   let PrintMethod = "printCPInstOperand";
251 }
252
253 def jtblock_operand : Operand<i32> {
254   let PrintMethod = "printJTBlockOperand";
255 }
256 def jt2block_operand : Operand<i32> {
257   let PrintMethod = "printJT2BlockOperand";
258 }
259
260 // Local PC labels.
261 def pclabel : Operand<i32> {
262   let PrintMethod = "printPCLabel";
263 }
264
265 // shifter_operand operands: so_reg and so_imm.
266 def so_reg : Operand<i32>,    // reg reg imm
267             ComplexPattern<i32, 3, "SelectShifterOperandReg",
268                             [shl,srl,sra,rotr]> {
269   let PrintMethod = "printSORegOperand";
270   let MIOperandInfo = (ops GPR, GPR, i32imm);
271 }
272
273 // so_imm - Match a 32-bit shifter_operand immediate operand, which is an
274 // 8-bit immediate rotated by an arbitrary number of bits.  so_imm values are
275 // represented in the imm field in the same 12-bit form that they are encoded
276 // into so_imm instructions: the 8-bit immediate is the least significant bits
277 // [bits 0-7], the 4-bit shift amount is the next 4 bits [bits 8-11].
278 def so_imm : Operand<i32>,
279              PatLeaf<(imm), [{
280       return ARM_AM::getSOImmVal(N->getZExtValue()) != -1;
281     }]> {
282   let PrintMethod = "printSOImmOperand";
283 }
284
285 // Break so_imm's up into two pieces.  This handles immediates with up to 16
286 // bits set in them.  This uses so_imm2part to match and so_imm2part_[12] to
287 // get the first/second pieces.
288 def so_imm2part : Operand<i32>,
289                   PatLeaf<(imm), [{
290       return ARM_AM::isSOImmTwoPartVal((unsigned)N->getZExtValue());
291     }]> {
292   let PrintMethod = "printSOImm2PartOperand";
293 }
294
295 def so_imm2part_1 : SDNodeXForm<imm, [{
296   unsigned V = ARM_AM::getSOImmTwoPartFirst((unsigned)N->getZExtValue());
297   return CurDAG->getTargetConstant(V, MVT::i32);
298 }]>;
299
300 def so_imm2part_2 : SDNodeXForm<imm, [{
301   unsigned V = ARM_AM::getSOImmTwoPartSecond((unsigned)N->getZExtValue());
302   return CurDAG->getTargetConstant(V, MVT::i32);
303 }]>;
304
305 def so_neg_imm2part : Operand<i32>, PatLeaf<(imm), [{
306       return ARM_AM::isSOImmTwoPartVal(-(int)N->getZExtValue());
307     }]> {
308   let PrintMethod = "printSOImm2PartOperand";
309 }
310
311 def so_neg_imm2part_1 : SDNodeXForm<imm, [{
312   unsigned V = ARM_AM::getSOImmTwoPartFirst(-(int)N->getZExtValue());
313   return CurDAG->getTargetConstant(V, MVT::i32);
314 }]>;
315
316 def so_neg_imm2part_2 : SDNodeXForm<imm, [{
317   unsigned V = ARM_AM::getSOImmTwoPartSecond(-(int)N->getZExtValue());
318   return CurDAG->getTargetConstant(V, MVT::i32);
319 }]>;
320
321 /// imm0_31 predicate - True if the 32-bit immediate is in the range [0,31].
322 def imm0_31 : Operand<i32>, PatLeaf<(imm), [{
323   return (int32_t)N->getZExtValue() < 32;
324 }]>;
325
326 // Define ARM specific addressing modes.
327
328 // addrmode2 := reg +/- reg shop imm
329 // addrmode2 := reg +/- imm12
330 //
331 def addrmode2 : Operand<i32>,
332                 ComplexPattern<i32, 3, "SelectAddrMode2", []> {
333   let PrintMethod = "printAddrMode2Operand";
334   let MIOperandInfo = (ops GPR:$base, GPR:$offsreg, i32imm:$offsimm);
335 }
336
337 def am2offset : Operand<i32>,
338                 ComplexPattern<i32, 2, "SelectAddrMode2Offset", []> {
339   let PrintMethod = "printAddrMode2OffsetOperand";
340   let MIOperandInfo = (ops GPR, i32imm);
341 }
342
343 // addrmode3 := reg +/- reg
344 // addrmode3 := reg +/- imm8
345 //
346 def addrmode3 : Operand<i32>,
347                 ComplexPattern<i32, 3, "SelectAddrMode3", []> {
348   let PrintMethod = "printAddrMode3Operand";
349   let MIOperandInfo = (ops GPR:$base, GPR:$offsreg, i32imm:$offsimm);
350 }
351
352 def am3offset : Operand<i32>,
353                 ComplexPattern<i32, 2, "SelectAddrMode3Offset", []> {
354   let PrintMethod = "printAddrMode3OffsetOperand";
355   let MIOperandInfo = (ops GPR, i32imm);
356 }
357
358 // addrmode4 := reg, <mode|W>
359 //
360 def addrmode4 : Operand<i32>,
361                 ComplexPattern<i32, 2, "SelectAddrMode4", []> {
362   let PrintMethod = "printAddrMode4Operand";
363   let MIOperandInfo = (ops GPR, i32imm);
364 }
365
366 // addrmode5 := reg +/- imm8*4
367 //
368 def addrmode5 : Operand<i32>,
369                 ComplexPattern<i32, 2, "SelectAddrMode5", []> {
370   let PrintMethod = "printAddrMode5Operand";
371   let MIOperandInfo = (ops GPR, i32imm);
372 }
373
374 // addrmode6 := reg with optional writeback
375 //
376 def addrmode6 : Operand<i32>,
377                 ComplexPattern<i32, 4, "SelectAddrMode6", []> {
378   let PrintMethod = "printAddrMode6Operand";
379   let MIOperandInfo = (ops GPR:$addr, GPR:$upd, i32imm, i32imm);
380 }
381
382 // addrmodepc := pc + reg
383 //
384 def addrmodepc : Operand<i32>,
385                  ComplexPattern<i32, 2, "SelectAddrModePC", []> {
386   let PrintMethod = "printAddrModePCOperand";
387   let MIOperandInfo = (ops GPR, i32imm);
388 }
389
390 def nohash_imm : Operand<i32> {
391   let PrintMethod = "printNoHashImmediate";
392 }
393
394 //===----------------------------------------------------------------------===//
395
396 include "ARMInstrFormats.td"
397
398 //===----------------------------------------------------------------------===//
399 // Multiclass helpers...
400 //
401
402 /// AsI1_bin_irs - Defines a set of (op r, {so_imm|r|so_reg}) patterns for a
403 /// binop that produces a value.
404 multiclass AsI1_bin_irs<bits<4> opcod, string opc, PatFrag opnode,
405                         bit Commutable = 0> {
406   def ri : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_imm:$b), DPFrm,
407                IIC_iALUi, opc, "\t$dst, $a, $b",
408                [(set GPR:$dst, (opnode GPR:$a, so_imm:$b))]> {
409     let Inst{25} = 1;
410   }
411   def rr : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, GPR:$b), DPFrm,
412                IIC_iALUr, opc, "\t$dst, $a, $b",
413                [(set GPR:$dst, (opnode GPR:$a, GPR:$b))]> {
414     let Inst{11-4} = 0b00000000;
415     let Inst{25} = 0;
416     let isCommutable = Commutable;
417   }
418   def rs : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_reg:$b), DPSoRegFrm,
419                IIC_iALUsr, opc, "\t$dst, $a, $b",
420                [(set GPR:$dst, (opnode GPR:$a, so_reg:$b))]> {
421     let Inst{25} = 0;
422   }
423 }
424
425 /// AI1_bin_s_irs - Similar to AsI1_bin_irs except it sets the 's' bit so the
426 /// instruction modifies the CPSR register.
427 let Defs = [CPSR] in {
428 multiclass AI1_bin_s_irs<bits<4> opcod, string opc, PatFrag opnode,
429                          bit Commutable = 0> {
430   def ri : AI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_imm:$b), DPFrm,
431                IIC_iALUi, opc, "\t$dst, $a, $b",
432                [(set GPR:$dst, (opnode GPR:$a, so_imm:$b))]> {
433     let Inst{20} = 1;
434     let Inst{25} = 1;
435   }
436   def rr : AI1<opcod, (outs GPR:$dst), (ins GPR:$a, GPR:$b), DPFrm,
437                IIC_iALUr, opc, "\t$dst, $a, $b",
438                [(set GPR:$dst, (opnode GPR:$a, GPR:$b))]> {
439     let isCommutable = Commutable;
440     let Inst{11-4} = 0b00000000;
441     let Inst{20} = 1;
442     let Inst{25} = 0;
443   }
444   def rs : AI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_reg:$b), DPSoRegFrm,
445                IIC_iALUsr, opc, "\t$dst, $a, $b",
446                [(set GPR:$dst, (opnode GPR:$a, so_reg:$b))]> {
447     let Inst{20} = 1;
448     let Inst{25} = 0;
449   }
450 }
451 }
452
453 /// AI1_cmp_irs - Defines a set of (op r, {so_imm|r|so_reg}) cmp / test
454 /// patterns. Similar to AsI1_bin_irs except the instruction does not produce
455 /// a explicit result, only implicitly set CPSR.
456 let Defs = [CPSR] in {
457 multiclass AI1_cmp_irs<bits<4> opcod, string opc, PatFrag opnode,
458                        bit Commutable = 0> {
459   def ri : AI1<opcod, (outs), (ins GPR:$a, so_imm:$b), DPFrm, IIC_iCMPi,
460                opc, "\t$a, $b",
461                [(opnode GPR:$a, so_imm:$b)]> {
462     let Inst{20} = 1;
463     let Inst{25} = 1;
464   }
465   def rr : AI1<opcod, (outs), (ins GPR:$a, GPR:$b), DPFrm, IIC_iCMPr,
466                opc, "\t$a, $b",
467                [(opnode GPR:$a, GPR:$b)]> {
468     let Inst{11-4} = 0b00000000;
469     let Inst{20} = 1;
470     let Inst{25} = 0;
471     let isCommutable = Commutable;
472   }
473   def rs : AI1<opcod, (outs), (ins GPR:$a, so_reg:$b), DPSoRegFrm, IIC_iCMPsr,
474                opc, "\t$a, $b",
475                [(opnode GPR:$a, so_reg:$b)]> {
476     let Inst{20} = 1;
477     let Inst{25} = 0;
478   }
479 }
480 }
481
482 /// AI_unary_rrot - A unary operation with two forms: one whose operand is a
483 /// register and one whose operand is a register rotated by 8/16/24.
484 /// FIXME: Remove the 'r' variant. Its rot_imm is zero.
485 multiclass AI_unary_rrot<bits<8> opcod, string opc, PatFrag opnode> {
486   def r     : AExtI<opcod, (outs GPR:$dst), (ins GPR:$src),
487                  IIC_iUNAr, opc, "\t$dst, $src",
488                  [(set GPR:$dst, (opnode GPR:$src))]>,
489               Requires<[IsARM, HasV6]> {
490     let Inst{11-10} = 0b00;
491     let Inst{19-16} = 0b1111;
492   }
493   def r_rot : AExtI<opcod, (outs GPR:$dst), (ins GPR:$src, i32imm:$rot),
494                  IIC_iUNAsi, opc, "\t$dst, $src, ror $rot",
495                  [(set GPR:$dst, (opnode (rotr GPR:$src, rot_imm:$rot)))]>,
496               Requires<[IsARM, HasV6]> {
497     let Inst{19-16} = 0b1111;
498   }
499 }
500
501 /// AI_bin_rrot - A binary operation with two forms: one whose operand is a
502 /// register and one whose operand is a register rotated by 8/16/24.
503 multiclass AI_bin_rrot<bits<8> opcod, string opc, PatFrag opnode> {
504   def rr     : AExtI<opcod, (outs GPR:$dst), (ins GPR:$LHS, GPR:$RHS),
505                   IIC_iALUr, opc, "\t$dst, $LHS, $RHS",
506                   [(set GPR:$dst, (opnode GPR:$LHS, GPR:$RHS))]>,
507                Requires<[IsARM, HasV6]> {
508     let Inst{11-10} = 0b00;
509   }
510   def rr_rot : AExtI<opcod, (outs GPR:$dst), (ins GPR:$LHS, GPR:$RHS, i32imm:$rot),
511                   IIC_iALUsi, opc, "\t$dst, $LHS, $RHS, ror $rot",
512                   [(set GPR:$dst, (opnode GPR:$LHS,
513                                           (rotr GPR:$RHS, rot_imm:$rot)))]>,
514                   Requires<[IsARM, HasV6]>;
515 }
516
517 /// AI1_adde_sube_irs - Define instructions and patterns for adde and sube.
518 let Uses = [CPSR] in {
519 multiclass AI1_adde_sube_irs<bits<4> opcod, string opc, PatFrag opnode,
520                              bit Commutable = 0> {
521   def ri : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_imm:$b),
522                 DPFrm, IIC_iALUi, opc, "\t$dst, $a, $b",
523                [(set GPR:$dst, (opnode GPR:$a, so_imm:$b))]>,
524                Requires<[IsARM, CarryDefIsUnused]> {
525     let Inst{25} = 1;
526   }
527   def rr : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
528                 DPFrm, IIC_iALUr, opc, "\t$dst, $a, $b",
529                [(set GPR:$dst, (opnode GPR:$a, GPR:$b))]>,
530                Requires<[IsARM, CarryDefIsUnused]> {
531     let isCommutable = Commutable;
532     let Inst{11-4} = 0b00000000;
533     let Inst{25} = 0;
534   }
535   def rs : AsI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_reg:$b),
536                 DPSoRegFrm, IIC_iALUsr, opc, "\t$dst, $a, $b",
537                [(set GPR:$dst, (opnode GPR:$a, so_reg:$b))]>,
538                Requires<[IsARM, CarryDefIsUnused]> {
539     let Inst{25} = 0;
540   }
541 }
542 // Carry setting variants
543 let Defs = [CPSR] in {
544 multiclass AI1_adde_sube_s_irs<bits<4> opcod, string opc, PatFrag opnode,
545                              bit Commutable = 0> {
546   def Sri : AXI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_imm:$b),
547                 DPFrm, IIC_iALUi, !strconcat(opc, "\t$dst, $a, $b"),
548                [(set GPR:$dst, (opnode GPR:$a, so_imm:$b))]>,
549                Requires<[IsARM, CarryDefIsUsed]> {
550     let Defs = [CPSR];
551     let Inst{20} = 1;
552     let Inst{25} = 1;
553   }
554   def Srr : AXI1<opcod, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
555                 DPFrm, IIC_iALUr, !strconcat(opc, "\t$dst, $a, $b"),
556                [(set GPR:$dst, (opnode GPR:$a, GPR:$b))]>,
557                Requires<[IsARM, CarryDefIsUsed]> {
558     let Defs = [CPSR];
559     let Inst{11-4} = 0b00000000;
560     let Inst{20} = 1;
561     let Inst{25} = 0;
562   }
563   def Srs : AXI1<opcod, (outs GPR:$dst), (ins GPR:$a, so_reg:$b),
564                 DPSoRegFrm, IIC_iALUsr, !strconcat(opc, "\t$dst, $a, $b"),
565                [(set GPR:$dst, (opnode GPR:$a, so_reg:$b))]>,
566                Requires<[IsARM, CarryDefIsUsed]> {
567     let Defs = [CPSR];
568     let Inst{20} = 1;
569     let Inst{25} = 0;
570   }
571 }
572 }
573 }
574
575 //===----------------------------------------------------------------------===//
576 // Instructions
577 //===----------------------------------------------------------------------===//
578
579 //===----------------------------------------------------------------------===//
580 //  Miscellaneous Instructions.
581 //
582
583 /// CONSTPOOL_ENTRY - This instruction represents a floating constant pool in
584 /// the function.  The first operand is the ID# for this instruction, the second
585 /// is the index into the MachineConstantPool that this is, the third is the
586 /// size in bytes of this constant pool entry.
587 let neverHasSideEffects = 1, isNotDuplicable = 1 in
588 def CONSTPOOL_ENTRY :
589 PseudoInst<(outs), (ins cpinst_operand:$instid, cpinst_operand:$cpidx,
590                     i32imm:$size), NoItinerary,
591            "${instid:label} ${cpidx:cpentry}", []>;
592
593 let Defs = [SP], Uses = [SP] in {
594 def ADJCALLSTACKUP :
595 PseudoInst<(outs), (ins i32imm:$amt1, i32imm:$amt2, pred:$p), NoItinerary,
596            "@ ADJCALLSTACKUP $amt1",
597            [(ARMcallseq_end timm:$amt1, timm:$amt2)]>;
598
599 def ADJCALLSTACKDOWN : 
600 PseudoInst<(outs), (ins i32imm:$amt, pred:$p), NoItinerary,
601            "@ ADJCALLSTACKDOWN $amt",
602            [(ARMcallseq_start timm:$amt)]>;
603 }
604
605 // Address computation and loads and stores in PIC mode.
606 let isNotDuplicable = 1 in {
607 def PICADD : AXI1<0b0100, (outs GPR:$dst), (ins GPR:$a, pclabel:$cp, pred:$p),
608                   Pseudo, IIC_iALUr, "\n$cp:\n\tadd$p\t$dst, pc, $a",
609                    [(set GPR:$dst, (ARMpic_add GPR:$a, imm:$cp))]>;
610
611 let AddedComplexity = 10 in {
612 def PICLDR  : AXI2ldw<(outs GPR:$dst), (ins addrmodepc:$addr, pred:$p),
613                   Pseudo, IIC_iLoadr, "\n${addr:label}:\n\tldr$p\t$dst, $addr",
614                   [(set GPR:$dst, (load addrmodepc:$addr))]>;
615
616 def PICLDRH : AXI3ldh<(outs GPR:$dst), (ins addrmodepc:$addr, pred:$p),
617                 Pseudo, IIC_iLoadr, "\n${addr:label}:\n\tldrh${p}\t$dst, $addr",
618                   [(set GPR:$dst, (zextloadi16 addrmodepc:$addr))]>;
619
620 def PICLDRB : AXI2ldb<(outs GPR:$dst), (ins addrmodepc:$addr, pred:$p),
621                 Pseudo, IIC_iLoadr, "\n${addr:label}:\n\tldrb${p}\t$dst, $addr",
622                   [(set GPR:$dst, (zextloadi8 addrmodepc:$addr))]>;
623
624 def PICLDRSH : AXI3ldsh<(outs GPR:$dst), (ins addrmodepc:$addr, pred:$p),
625                Pseudo, IIC_iLoadr, "\n${addr:label}:\n\tldrsh${p}\t$dst, $addr",
626                   [(set GPR:$dst, (sextloadi16 addrmodepc:$addr))]>;
627
628 def PICLDRSB : AXI3ldsb<(outs GPR:$dst), (ins addrmodepc:$addr, pred:$p),
629                Pseudo, IIC_iLoadr, "\n${addr:label}:\n\tldrsb${p}\t$dst, $addr",
630                   [(set GPR:$dst, (sextloadi8 addrmodepc:$addr))]>;
631 }
632 let AddedComplexity = 10 in {
633 def PICSTR  : AXI2stw<(outs), (ins GPR:$src, addrmodepc:$addr, pred:$p),
634                Pseudo, IIC_iStorer, "\n${addr:label}:\n\tstr$p\t$src, $addr",
635                [(store GPR:$src, addrmodepc:$addr)]>;
636
637 def PICSTRH : AXI3sth<(outs), (ins GPR:$src, addrmodepc:$addr, pred:$p),
638                Pseudo, IIC_iStorer, "\n${addr:label}:\n\tstrh${p}\t$src, $addr",
639                [(truncstorei16 GPR:$src, addrmodepc:$addr)]>;
640
641 def PICSTRB : AXI2stb<(outs), (ins GPR:$src, addrmodepc:$addr, pred:$p),
642                Pseudo, IIC_iStorer, "\n${addr:label}:\n\tstrb${p}\t$src, $addr",
643                [(truncstorei8 GPR:$src, addrmodepc:$addr)]>;
644 }
645 } // isNotDuplicable = 1
646
647
648 // LEApcrel - Load a pc-relative address into a register without offending the
649 // assembler.
650 def LEApcrel : AXI1<0x0, (outs GPR:$dst), (ins i32imm:$label, pred:$p),
651                     Pseudo, IIC_iALUi,
652            !strconcat(!strconcat(".set ${:private}PCRELV${:uid}, ($label-(",
653                                  "${:private}PCRELL${:uid}+8))\n"),
654                       !strconcat("${:private}PCRELL${:uid}:\n\t",
655                                  "add$p\t$dst, pc, #${:private}PCRELV${:uid}")),
656                    []>;
657
658 def LEApcrelJT : AXI1<0x0, (outs GPR:$dst),
659                            (ins i32imm:$label, nohash_imm:$id, pred:$p),
660           Pseudo, IIC_iALUi,
661    !strconcat(!strconcat(".set ${:private}PCRELV${:uid}, "
662                          "(${label}_${id}-(",
663                                   "${:private}PCRELL${:uid}+8))\n"),
664                        !strconcat("${:private}PCRELL${:uid}:\n\t",
665                                   "add$p\t$dst, pc, #${:private}PCRELV${:uid}")),
666                    []> {
667     let Inst{25} = 1;
668 }
669
670 //===----------------------------------------------------------------------===//
671 //  Control Flow Instructions.
672 //
673
674 let isReturn = 1, isTerminator = 1, isBarrier = 1 in
675   def BX_RET : AI<(outs), (ins), BrMiscFrm, IIC_Br, 
676                   "bx", "\tlr", [(ARMretflag)]> {
677   let Inst{3-0}   = 0b1110;
678   let Inst{7-4}   = 0b0001;
679   let Inst{19-8}  = 0b111111111111;
680   let Inst{27-20} = 0b00010010;
681 }
682
683 // Indirect branches
684 let isBranch = 1, isTerminator = 1, isBarrier = 1, isIndirectBranch = 1 in {
685   def BRIND : AXI<(outs), (ins GPR:$dst), BrMiscFrm, IIC_Br, "bx\t$dst",
686                   [(brind GPR:$dst)]> {
687     let Inst{7-4}   = 0b0001;
688     let Inst{19-8}  = 0b111111111111;
689     let Inst{27-20} = 0b00010010;
690     let Inst{31-28} = 0b1110;
691   }
692 }
693
694 // FIXME: remove when we have a way to marking a MI with these properties.
695 // FIXME: Should pc be an implicit operand like PICADD, etc?
696 let isReturn = 1, isTerminator = 1, isBarrier = 1, mayLoad = 1,
697     hasExtraDefRegAllocReq = 1 in
698   def LDM_RET : AXI4ld<(outs),
699                     (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
700                     LdStMulFrm, IIC_Br, "ldm${addr:submode}${p}\t$addr, $wb",
701                     []>;
702
703 // On non-Darwin platforms R9 is callee-saved.
704 let isCall = 1,
705   Defs = [R0,  R1,  R2,  R3,  R12, LR,
706           D0,  D1,  D2,  D3,  D4,  D5,  D6,  D7,
707           D16, D17, D18, D19, D20, D21, D22, D23,
708           D24, D25, D26, D27, D28, D29, D30, D31, CPSR, FPSCR] in {
709   def BL  : ABXI<0b1011, (outs), (ins i32imm:$func, variable_ops),
710                 IIC_Br, "bl\t${func:call}",
711                 [(ARMcall tglobaladdr:$func)]>,
712             Requires<[IsARM, IsNotDarwin]> {
713     let Inst{31-28} = 0b1110;
714   }
715
716   def BL_pred : ABI<0b1011, (outs), (ins i32imm:$func, variable_ops),
717                    IIC_Br, "bl", "\t${func:call}",
718                    [(ARMcall_pred tglobaladdr:$func)]>,
719                 Requires<[IsARM, IsNotDarwin]>;
720
721   // ARMv5T and above
722   def BLX : AXI<(outs), (ins GPR:$func, variable_ops), BrMiscFrm,
723                 IIC_Br, "blx\t$func",
724                 [(ARMcall GPR:$func)]>,
725             Requires<[IsARM, HasV5T, IsNotDarwin]> {
726     let Inst{7-4}   = 0b0011;
727     let Inst{19-8}  = 0b111111111111;
728     let Inst{27-20} = 0b00010010;
729   }
730
731   // ARMv4T
732   def BX : ABXIx2<(outs), (ins GPR:$func, variable_ops),
733                   IIC_Br, "mov\tlr, pc\n\tbx\t$func",
734                   [(ARMcall_nolink GPR:$func)]>,
735            Requires<[IsARM, IsNotDarwin]> {
736     let Inst{7-4}   = 0b0001;
737     let Inst{19-8}  = 0b111111111111;
738     let Inst{27-20} = 0b00010010;
739   }
740 }
741
742 // On Darwin R9 is call-clobbered.
743 let isCall = 1,
744   Defs = [R0,  R1,  R2,  R3,  R9,  R12, LR,
745           D0,  D1,  D2,  D3,  D4,  D5,  D6,  D7,
746           D16, D17, D18, D19, D20, D21, D22, D23,
747           D24, D25, D26, D27, D28, D29, D30, D31, CPSR, FPSCR] in {
748   def BLr9  : ABXI<0b1011, (outs), (ins i32imm:$func, variable_ops),
749                 IIC_Br, "bl\t${func:call}",
750                 [(ARMcall tglobaladdr:$func)]>, Requires<[IsARM, IsDarwin]> {
751     let Inst{31-28} = 0b1110;
752   }
753
754   def BLr9_pred : ABI<0b1011, (outs), (ins i32imm:$func, variable_ops),
755                    IIC_Br, "bl", "\t${func:call}",
756                    [(ARMcall_pred tglobaladdr:$func)]>,
757                   Requires<[IsARM, IsDarwin]>;
758
759   // ARMv5T and above
760   def BLXr9 : AXI<(outs), (ins GPR:$func, variable_ops), BrMiscFrm,
761                 IIC_Br, "blx\t$func",
762                 [(ARMcall GPR:$func)]>, Requires<[IsARM, HasV5T, IsDarwin]> {
763     let Inst{7-4}   = 0b0011;
764     let Inst{19-8}  = 0b111111111111;
765     let Inst{27-20} = 0b00010010;
766   }
767
768   // ARMv4T
769   def BXr9 : ABXIx2<(outs), (ins GPR:$func, variable_ops),
770                   IIC_Br, "mov\tlr, pc\n\tbx\t$func",
771                   [(ARMcall_nolink GPR:$func)]>, Requires<[IsARM, IsDarwin]> {
772     let Inst{7-4}   = 0b0001;
773     let Inst{19-8}  = 0b111111111111;
774     let Inst{27-20} = 0b00010010;
775   }
776 }
777
778 let isBranch = 1, isTerminator = 1 in {
779   // B is "predicable" since it can be xformed into a Bcc.
780   let isBarrier = 1 in {
781     let isPredicable = 1 in
782     def B : ABXI<0b1010, (outs), (ins brtarget:$target), IIC_Br,
783                 "b\t$target", [(br bb:$target)]>;
784
785   let isNotDuplicable = 1, isIndirectBranch = 1 in {
786   def BR_JTr : JTI<(outs), (ins GPR:$target, jtblock_operand:$jt, i32imm:$id),
787                     IIC_Br, "mov\tpc, $target \n$jt",
788                     [(ARMbrjt GPR:$target, tjumptable:$jt, imm:$id)]> {
789     let Inst{11-4}  = 0b00000000;
790     let Inst{15-12} = 0b1111;
791     let Inst{20}    = 0; // S Bit
792     let Inst{24-21} = 0b1101;
793     let Inst{27-25} = 0b000;
794   }
795   def BR_JTm : JTI<(outs),
796                    (ins addrmode2:$target, jtblock_operand:$jt, i32imm:$id),
797                    IIC_Br, "ldr\tpc, $target \n$jt",
798                    [(ARMbrjt (i32 (load addrmode2:$target)), tjumptable:$jt,
799                      imm:$id)]> {
800     let Inst{15-12} = 0b1111;
801     let Inst{20}    = 1; // L bit
802     let Inst{21}    = 0; // W bit
803     let Inst{22}    = 0; // B bit
804     let Inst{24}    = 1; // P bit
805     let Inst{27-25} = 0b011;
806   }
807   def BR_JTadd : JTI<(outs),
808                    (ins GPR:$target, GPR:$idx, jtblock_operand:$jt, i32imm:$id),
809                     IIC_Br, "add\tpc, $target, $idx \n$jt",
810                     [(ARMbrjt (add GPR:$target, GPR:$idx), tjumptable:$jt,
811                       imm:$id)]> {
812     let Inst{15-12} = 0b1111;
813     let Inst{20}    = 0; // S bit
814     let Inst{24-21} = 0b0100;
815     let Inst{27-25} = 0b000;
816   }
817   } // isNotDuplicable = 1, isIndirectBranch = 1
818   } // isBarrier = 1
819
820   // FIXME: should be able to write a pattern for ARMBrcond, but can't use
821   // a two-value operand where a dag node expects two operands. :( 
822   def Bcc : ABI<0b1010, (outs), (ins brtarget:$target),
823                IIC_Br, "b", "\t$target",
824                [/*(ARMbrcond bb:$target, imm:$cc, CCR:$ccr)*/]>;
825 }
826
827 //===----------------------------------------------------------------------===//
828 //  Load / store Instructions.
829 //
830
831 // Load
832 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in 
833 def LDR  : AI2ldw<(outs GPR:$dst), (ins addrmode2:$addr), LdFrm, IIC_iLoadr,
834                "ldr", "\t$dst, $addr",
835                [(set GPR:$dst, (load addrmode2:$addr))]>;
836
837 // Special LDR for loads from non-pc-relative constpools.
838 let canFoldAsLoad = 1, mayLoad = 1, isReMaterializable = 1,
839     mayHaveSideEffects = 1  in
840 def LDRcp : AI2ldw<(outs GPR:$dst), (ins addrmode2:$addr), LdFrm, IIC_iLoadr,
841                  "ldr", "\t$dst, $addr", []>;
842
843 // Loads with zero extension
844 def LDRH  : AI3ldh<(outs GPR:$dst), (ins addrmode3:$addr), LdMiscFrm,
845                   IIC_iLoadr, "ldrh", "\t$dst, $addr",
846                   [(set GPR:$dst, (zextloadi16 addrmode3:$addr))]>;
847
848 def LDRB  : AI2ldb<(outs GPR:$dst), (ins addrmode2:$addr), LdFrm, 
849                   IIC_iLoadr, "ldrb", "\t$dst, $addr",
850                   [(set GPR:$dst, (zextloadi8 addrmode2:$addr))]>;
851
852 // Loads with sign extension
853 def LDRSH : AI3ldsh<(outs GPR:$dst), (ins addrmode3:$addr), LdMiscFrm,
854                    IIC_iLoadr, "ldrsh", "\t$dst, $addr",
855                    [(set GPR:$dst, (sextloadi16 addrmode3:$addr))]>;
856
857 def LDRSB : AI3ldsb<(outs GPR:$dst), (ins addrmode3:$addr), LdMiscFrm,
858                    IIC_iLoadr, "ldrsb", "\t$dst, $addr",
859                    [(set GPR:$dst, (sextloadi8 addrmode3:$addr))]>;
860
861 let mayLoad = 1, hasExtraDefRegAllocReq = 1 in {
862 // Load doubleword
863 def LDRD : AI3ldd<(outs GPR:$dst1, GPR:$dst2), (ins addrmode3:$addr), LdMiscFrm,
864                  IIC_iLoadr, "ldrd", "\t$dst1, $addr",
865                  []>, Requires<[IsARM, HasV5TE]>;
866
867 // Indexed loads
868 def LDR_PRE  : AI2ldwpr<(outs GPR:$dst, GPR:$base_wb),
869                      (ins addrmode2:$addr), LdFrm, IIC_iLoadru,
870                      "ldr", "\t$dst, $addr!", "$addr.base = $base_wb", []>;
871
872 def LDR_POST : AI2ldwpo<(outs GPR:$dst, GPR:$base_wb),
873                      (ins GPR:$base, am2offset:$offset), LdFrm, IIC_iLoadru,
874                      "ldr", "\t$dst, [$base], $offset", "$base = $base_wb", []>;
875
876 def LDRH_PRE  : AI3ldhpr<(outs GPR:$dst, GPR:$base_wb),
877                      (ins addrmode3:$addr), LdMiscFrm, IIC_iLoadru,
878                      "ldrh", "\t$dst, $addr!", "$addr.base = $base_wb", []>;
879
880 def LDRH_POST : AI3ldhpo<(outs GPR:$dst, GPR:$base_wb),
881                      (ins GPR:$base,am3offset:$offset), LdMiscFrm, IIC_iLoadru,
882                     "ldrh", "\t$dst, [$base], $offset", "$base = $base_wb", []>;
883
884 def LDRB_PRE  : AI2ldbpr<(outs GPR:$dst, GPR:$base_wb),
885                      (ins addrmode2:$addr), LdFrm, IIC_iLoadru,
886                      "ldrb", "\t$dst, $addr!", "$addr.base = $base_wb", []>;
887
888 def LDRB_POST : AI2ldbpo<(outs GPR:$dst, GPR:$base_wb),
889                      (ins GPR:$base,am2offset:$offset), LdFrm, IIC_iLoadru,
890                     "ldrb", "\t$dst, [$base], $offset", "$base = $base_wb", []>;
891
892 def LDRSH_PRE : AI3ldshpr<(outs GPR:$dst, GPR:$base_wb),
893                       (ins addrmode3:$addr), LdMiscFrm, IIC_iLoadru,
894                       "ldrsh", "\t$dst, $addr!", "$addr.base = $base_wb", []>;
895
896 def LDRSH_POST: AI3ldshpo<(outs GPR:$dst, GPR:$base_wb),
897                       (ins GPR:$base,am3offset:$offset), LdMiscFrm, IIC_iLoadru,
898                    "ldrsh", "\t$dst, [$base], $offset", "$base = $base_wb", []>;
899
900 def LDRSB_PRE : AI3ldsbpr<(outs GPR:$dst, GPR:$base_wb),
901                       (ins addrmode3:$addr), LdMiscFrm, IIC_iLoadru,
902                       "ldrsb", "\t$dst, $addr!", "$addr.base = $base_wb", []>;
903
904 def LDRSB_POST: AI3ldsbpo<(outs GPR:$dst, GPR:$base_wb),
905                       (ins GPR:$base,am3offset:$offset), LdMiscFrm, IIC_iLoadru,
906                    "ldrsb", "\t$dst, [$base], $offset", "$base = $base_wb", []>;
907 }
908
909 // Store
910 def STR  : AI2stw<(outs), (ins GPR:$src, addrmode2:$addr), StFrm, IIC_iStorer,
911                "str", "\t$src, $addr",
912                [(store GPR:$src, addrmode2:$addr)]>;
913
914 // Stores with truncate
915 def STRH : AI3sth<(outs), (ins GPR:$src, addrmode3:$addr), StMiscFrm, IIC_iStorer,
916                "strh", "\t$src, $addr",
917                [(truncstorei16 GPR:$src, addrmode3:$addr)]>;
918
919 def STRB : AI2stb<(outs), (ins GPR:$src, addrmode2:$addr), StFrm, IIC_iStorer,
920                "strb", "\t$src, $addr",
921                [(truncstorei8 GPR:$src, addrmode2:$addr)]>;
922
923 // Store doubleword
924 let mayStore = 1, hasExtraSrcRegAllocReq = 1 in
925 def STRD : AI3std<(outs), (ins GPR:$src1, GPR:$src2, addrmode3:$addr),
926                StMiscFrm, IIC_iStorer,
927                "strd", "\t$src1, $addr", []>, Requires<[IsARM, HasV5TE]>;
928
929 // Indexed stores
930 def STR_PRE  : AI2stwpr<(outs GPR:$base_wb),
931                      (ins GPR:$src, GPR:$base, am2offset:$offset), 
932                      StFrm, IIC_iStoreru,
933                     "str", "\t$src, [$base, $offset]!", "$base = $base_wb",
934                     [(set GPR:$base_wb,
935                       (pre_store GPR:$src, GPR:$base, am2offset:$offset))]>;
936
937 def STR_POST : AI2stwpo<(outs GPR:$base_wb),
938                      (ins GPR:$src, GPR:$base,am2offset:$offset), 
939                      StFrm, IIC_iStoreru,
940                     "str", "\t$src, [$base], $offset", "$base = $base_wb",
941                     [(set GPR:$base_wb,
942                       (post_store GPR:$src, GPR:$base, am2offset:$offset))]>;
943
944 def STRH_PRE : AI3sthpr<(outs GPR:$base_wb),
945                      (ins GPR:$src, GPR:$base,am3offset:$offset), 
946                      StMiscFrm, IIC_iStoreru,
947                      "strh", "\t$src, [$base, $offset]!", "$base = $base_wb",
948                     [(set GPR:$base_wb,
949                       (pre_truncsti16 GPR:$src, GPR:$base,am3offset:$offset))]>;
950
951 def STRH_POST: AI3sthpo<(outs GPR:$base_wb),
952                      (ins GPR:$src, GPR:$base,am3offset:$offset), 
953                      StMiscFrm, IIC_iStoreru,
954                      "strh", "\t$src, [$base], $offset", "$base = $base_wb",
955                     [(set GPR:$base_wb, (post_truncsti16 GPR:$src,
956                                          GPR:$base, am3offset:$offset))]>;
957
958 def STRB_PRE : AI2stbpr<(outs GPR:$base_wb),
959                      (ins GPR:$src, GPR:$base,am2offset:$offset), 
960                      StFrm, IIC_iStoreru,
961                      "strb", "\t$src, [$base, $offset]!", "$base = $base_wb",
962                     [(set GPR:$base_wb, (pre_truncsti8 GPR:$src,
963                                          GPR:$base, am2offset:$offset))]>;
964
965 def STRB_POST: AI2stbpo<(outs GPR:$base_wb),
966                      (ins GPR:$src, GPR:$base,am2offset:$offset), 
967                      StFrm, IIC_iStoreru,
968                      "strb", "\t$src, [$base], $offset", "$base = $base_wb",
969                     [(set GPR:$base_wb, (post_truncsti8 GPR:$src,
970                                          GPR:$base, am2offset:$offset))]>;
971
972 //===----------------------------------------------------------------------===//
973 //  Load / store multiple Instructions.
974 //
975
976 let mayLoad = 1, hasExtraDefRegAllocReq = 1 in
977 def LDM : AXI4ld<(outs),
978                (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
979                LdStMulFrm, IIC_iLoadm, "ldm${addr:submode}${p}\t$addr, $wb",
980                []>;
981
982 let mayStore = 1, hasExtraSrcRegAllocReq = 1 in
983 def STM : AXI4st<(outs),
984                (ins addrmode4:$addr, pred:$p, reglist:$wb, variable_ops),
985                LdStMulFrm, IIC_iStorem, "stm${addr:submode}${p}\t$addr, $wb",
986                []>;
987
988 //===----------------------------------------------------------------------===//
989 //  Move Instructions.
990 //
991
992 let neverHasSideEffects = 1 in
993 def MOVr : AsI1<0b1101, (outs GPR:$dst), (ins GPR:$src), DPFrm, IIC_iMOVr,
994                 "mov", "\t$dst, $src", []>, UnaryDP {
995   let Inst{11-4} = 0b00000000;
996   let Inst{25} = 0;
997 }
998
999 def MOVs : AsI1<0b1101, (outs GPR:$dst), (ins so_reg:$src), 
1000                 DPSoRegFrm, IIC_iMOVsr,
1001                 "mov", "\t$dst, $src", [(set GPR:$dst, so_reg:$src)]>, UnaryDP {
1002   let Inst{25} = 0;
1003 }
1004
1005 let isReMaterializable = 1, isAsCheapAsAMove = 1 in
1006 def MOVi : AsI1<0b1101, (outs GPR:$dst), (ins so_imm:$src), DPFrm, IIC_iMOVi,
1007                 "mov", "\t$dst, $src", [(set GPR:$dst, so_imm:$src)]>, UnaryDP {
1008   let Inst{25} = 1;
1009 }
1010
1011 let isReMaterializable = 1, isAsCheapAsAMove = 1 in
1012 def MOVi16 : AI1<0b1000, (outs GPR:$dst), (ins i32imm:$src), 
1013                  DPFrm, IIC_iMOVi,
1014                  "movw", "\t$dst, $src",
1015                  [(set GPR:$dst, imm0_65535:$src)]>,
1016                  Requires<[IsARM, HasV6T2]> {
1017   let Inst{20} = 0;
1018   let Inst{25} = 1;
1019 }
1020
1021 let Constraints = "$src = $dst" in
1022 def MOVTi16 : AI1<0b1010, (outs GPR:$dst), (ins GPR:$src, i32imm:$imm),
1023                   DPFrm, IIC_iMOVi,
1024                   "movt", "\t$dst, $imm",
1025                   [(set GPR:$dst,
1026                         (or (and GPR:$src, 0xffff), 
1027                             lo16AllZero:$imm))]>, UnaryDP,
1028                   Requires<[IsARM, HasV6T2]> {
1029   let Inst{20} = 0;
1030   let Inst{25} = 1;
1031 }
1032
1033 def : ARMPat<(or GPR:$src, 0xffff0000), (MOVTi16 GPR:$src, 0xffff)>,
1034       Requires<[IsARM, HasV6T2]>;
1035
1036 let Uses = [CPSR] in
1037 def MOVrx : AsI1<0b1101, (outs GPR:$dst), (ins GPR:$src), Pseudo, IIC_iMOVsi,
1038                  "mov", "\t$dst, $src, rrx",
1039                  [(set GPR:$dst, (ARMrrx GPR:$src))]>, UnaryDP;
1040
1041 // These aren't really mov instructions, but we have to define them this way
1042 // due to flag operands.
1043
1044 let Defs = [CPSR] in {
1045 def MOVsrl_flag : AI1<0b1101, (outs GPR:$dst), (ins GPR:$src), Pseudo, 
1046                       IIC_iMOVsi, "movs", "\t$dst, $src, lsr #1",
1047                       [(set GPR:$dst, (ARMsrl_flag GPR:$src))]>, UnaryDP;
1048 def MOVsra_flag : AI1<0b1101, (outs GPR:$dst), (ins GPR:$src), Pseudo,
1049                       IIC_iMOVsi, "movs", "\t$dst, $src, asr #1",
1050                       [(set GPR:$dst, (ARMsra_flag GPR:$src))]>, UnaryDP;
1051 }
1052
1053 //===----------------------------------------------------------------------===//
1054 //  Extend Instructions.
1055 //
1056
1057 // Sign extenders
1058
1059 defm SXTB  : AI_unary_rrot<0b01101010,
1060                            "sxtb", UnOpFrag<(sext_inreg node:$Src, i8)>>;
1061 defm SXTH  : AI_unary_rrot<0b01101011,
1062                            "sxth", UnOpFrag<(sext_inreg node:$Src, i16)>>;
1063
1064 defm SXTAB : AI_bin_rrot<0b01101010,
1065                "sxtab", BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS, i8))>>;
1066 defm SXTAH : AI_bin_rrot<0b01101011,
1067                "sxtah", BinOpFrag<(add node:$LHS, (sext_inreg node:$RHS,i16))>>;
1068
1069 // TODO: SXT(A){B|H}16
1070
1071 // Zero extenders
1072
1073 let AddedComplexity = 16 in {
1074 defm UXTB   : AI_unary_rrot<0b01101110,
1075                             "uxtb"  , UnOpFrag<(and node:$Src, 0x000000FF)>>;
1076 defm UXTH   : AI_unary_rrot<0b01101111,
1077                             "uxth"  , UnOpFrag<(and node:$Src, 0x0000FFFF)>>;
1078 defm UXTB16 : AI_unary_rrot<0b01101100,
1079                             "uxtb16", UnOpFrag<(and node:$Src, 0x00FF00FF)>>;
1080
1081 def : ARMV6Pat<(and (shl GPR:$Src, (i32 8)), 0xFF00FF),
1082                (UXTB16r_rot GPR:$Src, 24)>;
1083 def : ARMV6Pat<(and (srl GPR:$Src, (i32 8)), 0xFF00FF),
1084                (UXTB16r_rot GPR:$Src, 8)>;
1085
1086 defm UXTAB : AI_bin_rrot<0b01101110, "uxtab",
1087                         BinOpFrag<(add node:$LHS, (and node:$RHS, 0x00FF))>>;
1088 defm UXTAH : AI_bin_rrot<0b01101111, "uxtah",
1089                         BinOpFrag<(add node:$LHS, (and node:$RHS, 0xFFFF))>>;
1090 }
1091
1092 // This isn't safe in general, the add is two 16-bit units, not a 32-bit add.
1093 //defm UXTAB16 : xxx<"uxtab16", 0xff00ff>;
1094
1095 // TODO: UXT(A){B|H}16
1096
1097 def SBFX  : I<(outs GPR:$dst),
1098               (ins GPR:$src, imm0_31:$lsb, imm0_31:$width),
1099                AddrMode1, Size4Bytes, IndexModeNone, DPFrm, IIC_iALUi,
1100                "sbfx", "\t$dst, $src, $lsb, $width", "", []>,
1101                Requires<[IsARM, HasV6T2]> {
1102   let Inst{27-21} = 0b0111101;
1103   let Inst{6-4}   = 0b101;
1104 }
1105
1106 def UBFX  : I<(outs GPR:$dst),
1107               (ins GPR:$src, imm0_31:$lsb, imm0_31:$width),
1108                AddrMode1, Size4Bytes, IndexModeNone, DPFrm, IIC_iALUi,
1109                "ubfx", "\t$dst, $src, $lsb, $width", "", []>,
1110                Requires<[IsARM, HasV6T2]> {
1111   let Inst{27-21} = 0b0111111;
1112   let Inst{6-4}   = 0b101;
1113 }
1114
1115 //===----------------------------------------------------------------------===//
1116 //  Arithmetic Instructions.
1117 //
1118
1119 defm ADD  : AsI1_bin_irs<0b0100, "add",
1120                          BinOpFrag<(add  node:$LHS, node:$RHS)>, 1>;
1121 defm SUB  : AsI1_bin_irs<0b0010, "sub",
1122                          BinOpFrag<(sub  node:$LHS, node:$RHS)>>;
1123
1124 // ADD and SUB with 's' bit set.
1125 defm ADDS : AI1_bin_s_irs<0b0100, "adds",
1126                           BinOpFrag<(addc node:$LHS, node:$RHS)>, 1>;
1127 defm SUBS : AI1_bin_s_irs<0b0010, "subs",
1128                           BinOpFrag<(subc node:$LHS, node:$RHS)>>;
1129
1130 defm ADC : AI1_adde_sube_irs<0b0101, "adc",
1131                              BinOpFrag<(adde node:$LHS, node:$RHS)>, 1>;
1132 defm SBC : AI1_adde_sube_irs<0b0110, "sbc",
1133                              BinOpFrag<(sube node:$LHS, node:$RHS)>>;
1134 defm ADCS : AI1_adde_sube_s_irs<0b0101, "adcs",
1135                              BinOpFrag<(adde node:$LHS, node:$RHS)>, 1>;
1136 defm SBCS : AI1_adde_sube_s_irs<0b0110, "sbcs",
1137                              BinOpFrag<(sube node:$LHS, node:$RHS)>>;
1138
1139 // These don't define reg/reg forms, because they are handled above.
1140 def RSBri : AsI1<0b0011, (outs GPR:$dst), (ins GPR:$a, so_imm:$b), DPFrm,
1141                   IIC_iALUi, "rsb", "\t$dst, $a, $b",
1142                   [(set GPR:$dst, (sub so_imm:$b, GPR:$a))]> {
1143     let Inst{25} = 1;
1144 }
1145
1146 def RSBrs : AsI1<0b0011, (outs GPR:$dst), (ins GPR:$a, so_reg:$b), DPSoRegFrm,
1147                   IIC_iALUsr, "rsb", "\t$dst, $a, $b",
1148                   [(set GPR:$dst, (sub so_reg:$b, GPR:$a))]> {
1149     let Inst{25} = 0;
1150 }
1151
1152 // RSB with 's' bit set.
1153 let Defs = [CPSR] in {
1154 def RSBSri : AI1<0b0011, (outs GPR:$dst), (ins GPR:$a, so_imm:$b), DPFrm,
1155                  IIC_iALUi, "rsbs", "\t$dst, $a, $b",
1156                  [(set GPR:$dst, (subc so_imm:$b, GPR:$a))]> {
1157     let Inst{20} = 1;
1158     let Inst{25} = 1;
1159 }
1160 def RSBSrs : AI1<0b0011, (outs GPR:$dst), (ins GPR:$a, so_reg:$b), DPSoRegFrm,
1161                  IIC_iALUsr, "rsbs", "\t$dst, $a, $b",
1162                  [(set GPR:$dst, (subc so_reg:$b, GPR:$a))]> {
1163     let Inst{20} = 1;
1164     let Inst{25} = 0;
1165 }
1166 }
1167
1168 let Uses = [CPSR] in {
1169 def RSCri : AsI1<0b0111, (outs GPR:$dst), (ins GPR:$a, so_imm:$b),
1170                  DPFrm, IIC_iALUi, "rsc", "\t$dst, $a, $b",
1171                  [(set GPR:$dst, (sube so_imm:$b, GPR:$a))]>,
1172                  Requires<[IsARM, CarryDefIsUnused]> {
1173     let Inst{25} = 1;
1174 }
1175 def RSCrs : AsI1<0b0111, (outs GPR:$dst), (ins GPR:$a, so_reg:$b),
1176                  DPSoRegFrm, IIC_iALUsr, "rsc", "\t$dst, $a, $b",
1177                  [(set GPR:$dst, (sube so_reg:$b, GPR:$a))]>,
1178                  Requires<[IsARM, CarryDefIsUnused]> {
1179     let Inst{25} = 0;
1180 }
1181 }
1182
1183 // FIXME: Allow these to be predicated.
1184 let Defs = [CPSR], Uses = [CPSR] in {
1185 def RSCSri : AXI1<0b0111, (outs GPR:$dst), (ins GPR:$a, so_imm:$b),
1186                   DPFrm, IIC_iALUi, "rscs\t$dst, $a, $b",
1187                   [(set GPR:$dst, (sube so_imm:$b, GPR:$a))]>,
1188                   Requires<[IsARM, CarryDefIsUnused]> {
1189     let Inst{20} = 1;
1190     let Inst{25} = 1;
1191 }
1192 def RSCSrs : AXI1<0b0111, (outs GPR:$dst), (ins GPR:$a, so_reg:$b),
1193                   DPSoRegFrm, IIC_iALUsr, "rscs\t$dst, $a, $b",
1194                   [(set GPR:$dst, (sube so_reg:$b, GPR:$a))]>,
1195                   Requires<[IsARM, CarryDefIsUnused]> {
1196     let Inst{20} = 1;
1197     let Inst{25} = 0;
1198 }
1199 }
1200
1201 // (sub X, imm) gets canonicalized to (add X, -imm).  Match this form.
1202 def : ARMPat<(add    GPR:$src, so_imm_neg:$imm),
1203              (SUBri  GPR:$src, so_imm_neg:$imm)>;
1204
1205 //def : ARMPat<(addc   GPR:$src, so_imm_neg:$imm),
1206 //             (SUBSri GPR:$src, so_imm_neg:$imm)>;
1207 //def : ARMPat<(adde   GPR:$src, so_imm_neg:$imm),
1208 //             (SBCri  GPR:$src, so_imm_neg:$imm)>;
1209
1210 // Note: These are implemented in C++ code, because they have to generate
1211 // ADD/SUBrs instructions, which use a complex pattern that a xform function
1212 // cannot produce.
1213 // (mul X, 2^n+1) -> (add (X << n), X)
1214 // (mul X, 2^n-1) -> (rsb X, (X << n))
1215
1216
1217 //===----------------------------------------------------------------------===//
1218 //  Bitwise Instructions.
1219 //
1220
1221 defm AND   : AsI1_bin_irs<0b0000, "and",
1222                           BinOpFrag<(and node:$LHS, node:$RHS)>, 1>;
1223 defm ORR   : AsI1_bin_irs<0b1100, "orr",
1224                           BinOpFrag<(or  node:$LHS, node:$RHS)>, 1>;
1225 defm EOR   : AsI1_bin_irs<0b0001, "eor",
1226                           BinOpFrag<(xor node:$LHS, node:$RHS)>, 1>;
1227 defm BIC   : AsI1_bin_irs<0b1110, "bic",
1228                           BinOpFrag<(and node:$LHS, (not node:$RHS))>>;
1229
1230 def BFC    : I<(outs GPR:$dst), (ins GPR:$src, bf_inv_mask_imm:$imm),
1231                AddrMode1, Size4Bytes, IndexModeNone, DPFrm, IIC_iUNAsi,
1232                "bfc", "\t$dst, $imm", "$src = $dst",
1233                [(set GPR:$dst, (and GPR:$src, bf_inv_mask_imm:$imm))]>,
1234                Requires<[IsARM, HasV6T2]> {
1235   let Inst{27-21} = 0b0111110;
1236   let Inst{6-0}   = 0b0011111;
1237 }
1238
1239 def  MVNr  : AsI1<0b1111, (outs GPR:$dst), (ins GPR:$src), DPFrm, IIC_iMOVr,
1240                   "mvn", "\t$dst, $src",
1241                   [(set GPR:$dst, (not GPR:$src))]>, UnaryDP {
1242   let Inst{11-4} = 0b00000000;
1243 }
1244 def  MVNs  : AsI1<0b1111, (outs GPR:$dst), (ins so_reg:$src), DPSoRegFrm,
1245                   IIC_iMOVsr, "mvn", "\t$dst, $src",
1246                   [(set GPR:$dst, (not so_reg:$src))]>, UnaryDP;
1247 let isReMaterializable = 1, isAsCheapAsAMove = 1 in
1248 def  MVNi  : AsI1<0b1111, (outs GPR:$dst), (ins so_imm:$imm), DPFrm, 
1249                   IIC_iMOVi, "mvn", "\t$dst, $imm",
1250                   [(set GPR:$dst, so_imm_not:$imm)]>,UnaryDP {
1251     let Inst{25} = 1;
1252 }
1253
1254 def : ARMPat<(and   GPR:$src, so_imm_not:$imm),
1255              (BICri GPR:$src, so_imm_not:$imm)>;
1256
1257 //===----------------------------------------------------------------------===//
1258 //  Multiply Instructions.
1259 //
1260
1261 let isCommutable = 1 in
1262 def MUL   : AsMul1I<0b0000000, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1263                    IIC_iMUL32, "mul", "\t$dst, $a, $b",
1264                    [(set GPR:$dst, (mul GPR:$a, GPR:$b))]>;
1265
1266 def MLA   : AsMul1I<0b0000001, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c),
1267                     IIC_iMAC32, "mla", "\t$dst, $a, $b, $c",
1268                    [(set GPR:$dst, (add (mul GPR:$a, GPR:$b), GPR:$c))]>;
1269
1270 def MLS   : AMul1I<0b0000011, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c),
1271                    IIC_iMAC32, "mls", "\t$dst, $a, $b, $c",
1272                    [(set GPR:$dst, (sub GPR:$c, (mul GPR:$a, GPR:$b)))]>,
1273                    Requires<[IsARM, HasV6T2]>;
1274
1275 // Extra precision multiplies with low / high results
1276 let neverHasSideEffects = 1 in {
1277 let isCommutable = 1 in {
1278 def SMULL : AsMul1I<0b0000110, (outs GPR:$ldst, GPR:$hdst),
1279                                (ins GPR:$a, GPR:$b), IIC_iMUL64,
1280                     "smull", "\t$ldst, $hdst, $a, $b", []>;
1281
1282 def UMULL : AsMul1I<0b0000100, (outs GPR:$ldst, GPR:$hdst),
1283                                (ins GPR:$a, GPR:$b), IIC_iMUL64,
1284                     "umull", "\t$ldst, $hdst, $a, $b", []>;
1285 }
1286
1287 // Multiply + accumulate
1288 def SMLAL : AsMul1I<0b0000111, (outs GPR:$ldst, GPR:$hdst),
1289                                (ins GPR:$a, GPR:$b), IIC_iMAC64,
1290                     "smlal", "\t$ldst, $hdst, $a, $b", []>;
1291
1292 def UMLAL : AsMul1I<0b0000101, (outs GPR:$ldst, GPR:$hdst),
1293                                (ins GPR:$a, GPR:$b), IIC_iMAC64,
1294                     "umlal", "\t$ldst, $hdst, $a, $b", []>;
1295
1296 def UMAAL : AMul1I <0b0000010, (outs GPR:$ldst, GPR:$hdst),
1297                                (ins GPR:$a, GPR:$b), IIC_iMAC64,
1298                     "umaal", "\t$ldst, $hdst, $a, $b", []>,
1299                     Requires<[IsARM, HasV6]>;
1300 } // neverHasSideEffects
1301
1302 // Most significant word multiply
1303 def SMMUL : AMul2I <0b0111010, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1304                IIC_iMUL32, "smmul", "\t$dst, $a, $b",
1305                [(set GPR:$dst, (mulhs GPR:$a, GPR:$b))]>,
1306             Requires<[IsARM, HasV6]> {
1307   let Inst{7-4}   = 0b0001;
1308   let Inst{15-12} = 0b1111;
1309 }
1310
1311 def SMMLA : AMul2I <0b0111010, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c),
1312                IIC_iMAC32, "smmla", "\t$dst, $a, $b, $c",
1313                [(set GPR:$dst, (add (mulhs GPR:$a, GPR:$b), GPR:$c))]>,
1314             Requires<[IsARM, HasV6]> {
1315   let Inst{7-4}   = 0b0001;
1316 }
1317
1318
1319 def SMMLS : AMul2I <0b0111010, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$c),
1320                IIC_iMAC32, "smmls", "\t$dst, $a, $b, $c",
1321                [(set GPR:$dst, (sub GPR:$c, (mulhs GPR:$a, GPR:$b)))]>,
1322             Requires<[IsARM, HasV6]> {
1323   let Inst{7-4}   = 0b1101;
1324 }
1325
1326 multiclass AI_smul<string opc, PatFrag opnode> {
1327   def BB : AMulxyI<0b0001011, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1328               IIC_iMUL32, !strconcat(opc, "bb"), "\t$dst, $a, $b",
1329               [(set GPR:$dst, (opnode (sext_inreg GPR:$a, i16),
1330                                       (sext_inreg GPR:$b, i16)))]>,
1331            Requires<[IsARM, HasV5TE]> {
1332              let Inst{5} = 0;
1333              let Inst{6} = 0;
1334            }
1335
1336   def BT : AMulxyI<0b0001011, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1337               IIC_iMUL32, !strconcat(opc, "bt"), "\t$dst, $a, $b",
1338               [(set GPR:$dst, (opnode (sext_inreg GPR:$a, i16),
1339                                       (sra GPR:$b, (i32 16))))]>,
1340            Requires<[IsARM, HasV5TE]> {
1341              let Inst{5} = 0;
1342              let Inst{6} = 1;
1343            }
1344
1345   def TB : AMulxyI<0b0001011, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1346               IIC_iMUL32, !strconcat(opc, "tb"), "\t$dst, $a, $b",
1347               [(set GPR:$dst, (opnode (sra GPR:$a, (i32 16)),
1348                                       (sext_inreg GPR:$b, i16)))]>,
1349            Requires<[IsARM, HasV5TE]> {
1350              let Inst{5} = 1;
1351              let Inst{6} = 0;
1352            }
1353
1354   def TT : AMulxyI<0b0001011, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1355               IIC_iMUL32, !strconcat(opc, "tt"), "\t$dst, $a, $b",
1356               [(set GPR:$dst, (opnode (sra GPR:$a, (i32 16)),
1357                                       (sra GPR:$b, (i32 16))))]>,
1358             Requires<[IsARM, HasV5TE]> {
1359              let Inst{5} = 1;
1360              let Inst{6} = 1;
1361            }
1362
1363   def WB : AMulxyI<0b0001001, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1364               IIC_iMUL16, !strconcat(opc, "wb"), "\t$dst, $a, $b",
1365               [(set GPR:$dst, (sra (opnode GPR:$a,
1366                                     (sext_inreg GPR:$b, i16)), (i32 16)))]>,
1367            Requires<[IsARM, HasV5TE]> {
1368              let Inst{5} = 1;
1369              let Inst{6} = 0;
1370            }
1371
1372   def WT : AMulxyI<0b0001001, (outs GPR:$dst), (ins GPR:$a, GPR:$b),
1373               IIC_iMUL16, !strconcat(opc, "wt"), "\t$dst, $a, $b",
1374               [(set GPR:$dst, (sra (opnode GPR:$a,
1375                                     (sra GPR:$b, (i32 16))), (i32 16)))]>,
1376             Requires<[IsARM, HasV5TE]> {
1377              let Inst{5} = 1;
1378              let Inst{6} = 1;
1379            }
1380 }
1381
1382
1383 multiclass AI_smla<string opc, PatFrag opnode> {
1384   def BB : AMulxyI<0b0001000, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1385               IIC_iMAC16, !strconcat(opc, "bb"), "\t$dst, $a, $b, $acc",
1386               [(set GPR:$dst, (add GPR:$acc,
1387                                (opnode (sext_inreg GPR:$a, i16),
1388                                        (sext_inreg GPR:$b, i16))))]>,
1389            Requires<[IsARM, HasV5TE]> {
1390              let Inst{5} = 0;
1391              let Inst{6} = 0;
1392            }
1393
1394   def BT : AMulxyI<0b0001000, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1395               IIC_iMAC16, !strconcat(opc, "bt"), "\t$dst, $a, $b, $acc",
1396               [(set GPR:$dst, (add GPR:$acc, (opnode (sext_inreg GPR:$a, i16),
1397                                                      (sra GPR:$b, (i32 16)))))]>,
1398            Requires<[IsARM, HasV5TE]> {
1399              let Inst{5} = 0;
1400              let Inst{6} = 1;
1401            }
1402
1403   def TB : AMulxyI<0b0001000, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1404               IIC_iMAC16, !strconcat(opc, "tb"), "\t$dst, $a, $b, $acc",
1405               [(set GPR:$dst, (add GPR:$acc, (opnode (sra GPR:$a, (i32 16)),
1406                                                  (sext_inreg GPR:$b, i16))))]>,
1407            Requires<[IsARM, HasV5TE]> {
1408              let Inst{5} = 1;
1409              let Inst{6} = 0;
1410            }
1411
1412   def TT : AMulxyI<0b0001000, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1413               IIC_iMAC16, !strconcat(opc, "tt"), "\t$dst, $a, $b, $acc",
1414              [(set GPR:$dst, (add GPR:$acc, (opnode (sra GPR:$a, (i32 16)),
1415                                                     (sra GPR:$b, (i32 16)))))]>,
1416             Requires<[IsARM, HasV5TE]> {
1417              let Inst{5} = 1;
1418              let Inst{6} = 1;
1419            }
1420
1421   def WB : AMulxyI<0b0001001, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1422               IIC_iMAC16, !strconcat(opc, "wb"), "\t$dst, $a, $b, $acc",
1423               [(set GPR:$dst, (add GPR:$acc, (sra (opnode GPR:$a,
1424                                        (sext_inreg GPR:$b, i16)), (i32 16))))]>,
1425            Requires<[IsARM, HasV5TE]> {
1426              let Inst{5} = 0;
1427              let Inst{6} = 0;
1428            }
1429
1430   def WT : AMulxyI<0b0001001, (outs GPR:$dst), (ins GPR:$a, GPR:$b, GPR:$acc),
1431               IIC_iMAC16, !strconcat(opc, "wt"), "\t$dst, $a, $b, $acc",
1432               [(set GPR:$dst, (add GPR:$acc, (sra (opnode GPR:$a,
1433                                          (sra GPR:$b, (i32 16))), (i32 16))))]>,
1434             Requires<[IsARM, HasV5TE]> {
1435              let Inst{5} = 0;
1436              let Inst{6} = 1;
1437            }
1438 }
1439
1440 defm SMUL : AI_smul<"smul", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1441 defm SMLA : AI_smla<"smla", BinOpFrag<(mul node:$LHS, node:$RHS)>>;
1442
1443 // TODO: Halfword multiple accumulate long: SMLAL<x><y>
1444 // TODO: Dual halfword multiple: SMUAD, SMUSD, SMLAD, SMLSD, SMLALD, SMLSLD
1445
1446 //===----------------------------------------------------------------------===//
1447 //  Misc. Arithmetic Instructions.
1448 //
1449
1450 def CLZ  : AMiscA1I<0b000010110, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1451               "clz", "\t$dst, $src",
1452               [(set GPR:$dst, (ctlz GPR:$src))]>, Requires<[IsARM, HasV5T]> {
1453   let Inst{7-4}   = 0b0001;
1454   let Inst{11-8}  = 0b1111;
1455   let Inst{19-16} = 0b1111;
1456 }
1457
1458 def RBIT : AMiscA1I<0b01101111, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1459               "rbit", "\t$dst, $src", []>, Requires<[IsARM, HasV6T2]> {
1460   let Inst{7-4}   = 0b0011;
1461   let Inst{11-8}  = 0b1111;
1462   let Inst{19-16} = 0b1111;
1463 }
1464
1465 def REV  : AMiscA1I<0b01101011, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1466               "rev", "\t$dst, $src",
1467               [(set GPR:$dst, (bswap GPR:$src))]>, Requires<[IsARM, HasV6]> {
1468   let Inst{7-4}   = 0b0011;
1469   let Inst{11-8}  = 0b1111;
1470   let Inst{19-16} = 0b1111;
1471 }
1472
1473 def REV16 : AMiscA1I<0b01101011, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1474                "rev16", "\t$dst, $src",
1475                [(set GPR:$dst,
1476                    (or (and (srl GPR:$src, (i32 8)), 0xFF),
1477                        (or (and (shl GPR:$src, (i32 8)), 0xFF00),
1478                            (or (and (srl GPR:$src, (i32 8)), 0xFF0000),
1479                                (and (shl GPR:$src, (i32 8)), 0xFF000000)))))]>,
1480                Requires<[IsARM, HasV6]> {
1481   let Inst{7-4}   = 0b1011;
1482   let Inst{11-8}  = 0b1111;
1483   let Inst{19-16} = 0b1111;
1484 }
1485
1486 def REVSH : AMiscA1I<0b01101111, (outs GPR:$dst), (ins GPR:$src), IIC_iUNAr,
1487                "revsh", "\t$dst, $src",
1488                [(set GPR:$dst,
1489                   (sext_inreg
1490                     (or (srl (and GPR:$src, 0xFF00), (i32 8)),
1491                         (shl GPR:$src, (i32 8))), i16))]>,
1492                Requires<[IsARM, HasV6]> {
1493   let Inst{7-4}   = 0b1011;
1494   let Inst{11-8}  = 0b1111;
1495   let Inst{19-16} = 0b1111;
1496 }
1497
1498 def PKHBT : AMiscA1I<0b01101000, (outs GPR:$dst),
1499                                  (ins GPR:$src1, GPR:$src2, i32imm:$shamt),
1500                IIC_iALUsi, "pkhbt", "\t$dst, $src1, $src2, LSL $shamt",
1501                [(set GPR:$dst, (or (and GPR:$src1, 0xFFFF),
1502                                    (and (shl GPR:$src2, (i32 imm:$shamt)),
1503                                         0xFFFF0000)))]>,
1504                Requires<[IsARM, HasV6]> {
1505   let Inst{6-4} = 0b001;
1506 }
1507
1508 // Alternate cases for PKHBT where identities eliminate some nodes.
1509 def : ARMV6Pat<(or (and GPR:$src1, 0xFFFF), (and GPR:$src2, 0xFFFF0000)),
1510                (PKHBT GPR:$src1, GPR:$src2, 0)>;
1511 def : ARMV6Pat<(or (and GPR:$src1, 0xFFFF), (shl GPR:$src2, imm16_31:$shamt)),
1512                (PKHBT GPR:$src1, GPR:$src2, imm16_31:$shamt)>;
1513
1514
1515 def PKHTB : AMiscA1I<0b01101000, (outs GPR:$dst),
1516                                  (ins GPR:$src1, GPR:$src2, i32imm:$shamt),
1517                IIC_iALUsi, "pkhtb", "\t$dst, $src1, $src2, ASR $shamt",
1518                [(set GPR:$dst, (or (and GPR:$src1, 0xFFFF0000),
1519                                    (and (sra GPR:$src2, imm16_31:$shamt),
1520                                         0xFFFF)))]>, Requires<[IsARM, HasV6]> {
1521   let Inst{6-4} = 0b101;
1522 }
1523
1524 // Alternate cases for PKHTB where identities eliminate some nodes.  Note that
1525 // a shift amount of 0 is *not legal* here, it is PKHBT instead.
1526 def : ARMV6Pat<(or (and GPR:$src1, 0xFFFF0000), (srl GPR:$src2, (i32 16))),
1527                (PKHTB GPR:$src1, GPR:$src2, 16)>;
1528 def : ARMV6Pat<(or (and GPR:$src1, 0xFFFF0000),
1529                    (and (srl GPR:$src2, imm1_15:$shamt), 0xFFFF)),
1530                (PKHTB GPR:$src1, GPR:$src2, imm1_15:$shamt)>;
1531
1532 //===----------------------------------------------------------------------===//
1533 //  Comparison Instructions...
1534 //
1535
1536 defm CMP  : AI1_cmp_irs<0b1010, "cmp",
1537                         BinOpFrag<(ARMcmp node:$LHS, node:$RHS)>>;
1538 defm CMN  : AI1_cmp_irs<0b1011, "cmn",
1539                         BinOpFrag<(ARMcmp node:$LHS,(ineg node:$RHS))>>;
1540
1541 // Note that TST/TEQ don't set all the same flags that CMP does!
1542 defm TST  : AI1_cmp_irs<0b1000, "tst",
1543                         BinOpFrag<(ARMcmpZ (and node:$LHS, node:$RHS), 0)>, 1>;
1544 defm TEQ  : AI1_cmp_irs<0b1001, "teq",
1545                         BinOpFrag<(ARMcmpZ (xor node:$LHS, node:$RHS), 0)>, 1>;
1546
1547 defm CMPz  : AI1_cmp_irs<0b1010, "cmp",
1548                          BinOpFrag<(ARMcmpZ node:$LHS, node:$RHS)>>;
1549 defm CMNz  : AI1_cmp_irs<0b1011, "cmn",
1550                          BinOpFrag<(ARMcmpZ node:$LHS,(ineg node:$RHS))>>;
1551
1552 def : ARMPat<(ARMcmp GPR:$src, so_imm_neg:$imm),
1553              (CMNri  GPR:$src, so_imm_neg:$imm)>;
1554
1555 def : ARMPat<(ARMcmpZ GPR:$src, so_imm_neg:$imm),
1556              (CMNri  GPR:$src, so_imm_neg:$imm)>;
1557
1558
1559 // Conditional moves
1560 // FIXME: should be able to write a pattern for ARMcmov, but can't use
1561 // a two-value operand where a dag node expects two operands. :( 
1562 def MOVCCr : AI1<0b1101, (outs GPR:$dst), (ins GPR:$false, GPR:$true), DPFrm,
1563                 IIC_iCMOVr, "mov", "\t$dst, $true",
1564       [/*(set GPR:$dst, (ARMcmov GPR:$false, GPR:$true, imm:$cc, CCR:$ccr))*/]>,
1565                 RegConstraint<"$false = $dst">, UnaryDP {
1566   let Inst{11-4} = 0b00000000;
1567   let Inst{25} = 0;
1568 }
1569
1570 def MOVCCs : AI1<0b1101, (outs GPR:$dst),
1571                         (ins GPR:$false, so_reg:$true), DPSoRegFrm, IIC_iCMOVsr,
1572                 "mov", "\t$dst, $true",
1573    [/*(set GPR:$dst, (ARMcmov GPR:$false, so_reg:$true, imm:$cc, CCR:$ccr))*/]>,
1574                 RegConstraint<"$false = $dst">, UnaryDP {
1575   let Inst{25} = 0;
1576 }
1577
1578 def MOVCCi : AI1<0b1101, (outs GPR:$dst),
1579                         (ins GPR:$false, so_imm:$true), DPFrm, IIC_iCMOVi,
1580                 "mov", "\t$dst, $true",
1581    [/*(set GPR:$dst, (ARMcmov GPR:$false, so_imm:$true, imm:$cc, CCR:$ccr))*/]>,
1582                 RegConstraint<"$false = $dst">, UnaryDP {
1583   let Inst{25} = 1;
1584 }
1585
1586 //===----------------------------------------------------------------------===//
1587 // Atomic operations intrinsics
1588 //
1589
1590 // memory barriers protect the atomic sequences
1591 let hasSideEffects = 1 in {
1592 def Int_MemBarrierV7 : AInoP<(outs), (ins),
1593                         Pseudo, NoItinerary,
1594                         "dmb", "",
1595                         [(ARMMemBarrierV7)]>,
1596                         Requires<[IsARM, HasV7]> {
1597   let Inst{31-4} = 0xf57ff05;
1598   // FIXME: add support for options other than a full system DMB
1599   let Inst{3-0} = 0b1111;
1600 }
1601
1602 def Int_SyncBarrierV7 : AInoP<(outs), (ins),
1603                         Pseudo, NoItinerary,
1604                         "dsb", "",
1605                         [(ARMSyncBarrierV7)]>,
1606                         Requires<[IsARM, HasV7]> {
1607   let Inst{31-4} = 0xf57ff04;
1608   // FIXME: add support for options other than a full system DSB
1609   let Inst{3-0} = 0b1111;
1610 }
1611
1612 def Int_MemBarrierV6 : AInoP<(outs), (ins GPR:$zero),
1613                        Pseudo, NoItinerary,
1614                        "mcr", "\tp15, 0, $zero, c7, c10, 5",
1615                        [(ARMMemBarrierV6 GPR:$zero)]>,
1616                        Requires<[IsARM, HasV6]> {
1617   // FIXME: add support for options other than a full system DMB
1618   // FIXME: add encoding
1619 }
1620
1621 def Int_SyncBarrierV6 : AInoP<(outs), (ins GPR:$zero),
1622                         Pseudo, NoItinerary,
1623                         "mcr", "\tp15, 0, $zero, c7, c10, 4",
1624                         [(ARMSyncBarrierV6 GPR:$zero)]>,
1625                         Requires<[IsARM, HasV6]> {
1626   // FIXME: add support for options other than a full system DSB
1627   // FIXME: add encoding
1628 }
1629 }
1630
1631 let usesCustomInserter = 1 in {
1632   let Uses = [CPSR] in {
1633     def ATOMIC_LOAD_ADD_I8 : PseudoInst<
1634       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1635       "${:comment} ATOMIC_LOAD_ADD_I8 PSEUDO!",
1636       [(set GPR:$dst, (atomic_load_add_8 GPR:$ptr, GPR:$incr))]>;
1637     def ATOMIC_LOAD_SUB_I8 : PseudoInst<
1638       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1639       "${:comment} ATOMIC_LOAD_SUB_I8 PSEUDO!",
1640       [(set GPR:$dst, (atomic_load_sub_8 GPR:$ptr, GPR:$incr))]>;
1641     def ATOMIC_LOAD_AND_I8 : PseudoInst<
1642       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1643       "${:comment} ATOMIC_LOAD_AND_I8 PSEUDO!",
1644       [(set GPR:$dst, (atomic_load_and_8 GPR:$ptr, GPR:$incr))]>;
1645     def ATOMIC_LOAD_OR_I8 : PseudoInst<
1646       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1647       "${:comment} ATOMIC_LOAD_OR_I8 PSEUDO!",
1648       [(set GPR:$dst, (atomic_load_or_8 GPR:$ptr, GPR:$incr))]>;
1649     def ATOMIC_LOAD_XOR_I8 : PseudoInst<
1650       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1651       "${:comment} ATOMIC_LOAD_XOR_I8 PSEUDO!",
1652       [(set GPR:$dst, (atomic_load_xor_8 GPR:$ptr, GPR:$incr))]>;
1653     def ATOMIC_LOAD_NAND_I8 : PseudoInst<
1654       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1655       "${:comment} ATOMIC_LOAD_NAND_I8 PSEUDO!",
1656       [(set GPR:$dst, (atomic_load_nand_8 GPR:$ptr, GPR:$incr))]>;
1657     def ATOMIC_LOAD_ADD_I16 : PseudoInst<
1658       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1659       "${:comment} ATOMIC_LOAD_ADD_I16 PSEUDO!",
1660       [(set GPR:$dst, (atomic_load_add_16 GPR:$ptr, GPR:$incr))]>;
1661     def ATOMIC_LOAD_SUB_I16 : PseudoInst<
1662       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1663       "${:comment} ATOMIC_LOAD_SUB_I16 PSEUDO!",
1664       [(set GPR:$dst, (atomic_load_sub_16 GPR:$ptr, GPR:$incr))]>;
1665     def ATOMIC_LOAD_AND_I16 : PseudoInst<
1666       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1667       "${:comment} ATOMIC_LOAD_AND_I16 PSEUDO!",
1668       [(set GPR:$dst, (atomic_load_and_16 GPR:$ptr, GPR:$incr))]>;
1669     def ATOMIC_LOAD_OR_I16 : PseudoInst<
1670       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1671       "${:comment} ATOMIC_LOAD_OR_I16 PSEUDO!",
1672       [(set GPR:$dst, (atomic_load_or_16 GPR:$ptr, GPR:$incr))]>;
1673     def ATOMIC_LOAD_XOR_I16 : PseudoInst<
1674       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1675       "${:comment} ATOMIC_LOAD_XOR_I16 PSEUDO!",
1676       [(set GPR:$dst, (atomic_load_xor_16 GPR:$ptr, GPR:$incr))]>;
1677     def ATOMIC_LOAD_NAND_I16 : PseudoInst<
1678       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1679       "${:comment} ATOMIC_LOAD_NAND_I16 PSEUDO!",
1680       [(set GPR:$dst, (atomic_load_nand_16 GPR:$ptr, GPR:$incr))]>;
1681     def ATOMIC_LOAD_ADD_I32 : PseudoInst<
1682       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1683       "${:comment} ATOMIC_LOAD_ADD_I32 PSEUDO!",
1684       [(set GPR:$dst, (atomic_load_add_32 GPR:$ptr, GPR:$incr))]>;
1685     def ATOMIC_LOAD_SUB_I32 : PseudoInst<
1686       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1687       "${:comment} ATOMIC_LOAD_SUB_I32 PSEUDO!",
1688       [(set GPR:$dst, (atomic_load_sub_32 GPR:$ptr, GPR:$incr))]>;
1689     def ATOMIC_LOAD_AND_I32 : PseudoInst<
1690       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1691       "${:comment} ATOMIC_LOAD_AND_I32 PSEUDO!",
1692       [(set GPR:$dst, (atomic_load_and_32 GPR:$ptr, GPR:$incr))]>;
1693     def ATOMIC_LOAD_OR_I32 : PseudoInst<
1694       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1695       "${:comment} ATOMIC_LOAD_OR_I32 PSEUDO!",
1696       [(set GPR:$dst, (atomic_load_or_32 GPR:$ptr, GPR:$incr))]>;
1697     def ATOMIC_LOAD_XOR_I32 : PseudoInst<
1698       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1699       "${:comment} ATOMIC_LOAD_XOR_I32 PSEUDO!",
1700       [(set GPR:$dst, (atomic_load_xor_32 GPR:$ptr, GPR:$incr))]>;
1701     def ATOMIC_LOAD_NAND_I32 : PseudoInst<
1702       (outs GPR:$dst), (ins GPR:$ptr, GPR:$incr), NoItinerary,
1703       "${:comment} ATOMIC_LOAD_NAND_I32 PSEUDO!",
1704       [(set GPR:$dst, (atomic_load_nand_32 GPR:$ptr, GPR:$incr))]>;
1705
1706     def ATOMIC_SWAP_I8 : PseudoInst<
1707       (outs GPR:$dst), (ins GPR:$ptr, GPR:$new), NoItinerary,
1708       "${:comment} ATOMIC_SWAP_I8 PSEUDO!",
1709       [(set GPR:$dst, (atomic_swap_8 GPR:$ptr, GPR:$new))]>;
1710     def ATOMIC_SWAP_I16 : PseudoInst<
1711       (outs GPR:$dst), (ins GPR:$ptr, GPR:$new), NoItinerary,
1712       "${:comment} ATOMIC_SWAP_I16 PSEUDO!",
1713       [(set GPR:$dst, (atomic_swap_16 GPR:$ptr, GPR:$new))]>;
1714     def ATOMIC_SWAP_I32 : PseudoInst<
1715       (outs GPR:$dst), (ins GPR:$ptr, GPR:$new), NoItinerary,
1716       "${:comment} ATOMIC_SWAP_I32 PSEUDO!",
1717       [(set GPR:$dst, (atomic_swap_32 GPR:$ptr, GPR:$new))]>;
1718
1719     def ATOMIC_CMP_SWAP_I8 : PseudoInst<
1720       (outs GPR:$dst), (ins GPR:$ptr, GPR:$old, GPR:$new), NoItinerary,
1721       "${:comment} ATOMIC_CMP_SWAP_I8 PSEUDO!",
1722       [(set GPR:$dst, (atomic_cmp_swap_8 GPR:$ptr, GPR:$old, GPR:$new))]>;
1723     def ATOMIC_CMP_SWAP_I16 : PseudoInst<
1724       (outs GPR:$dst), (ins GPR:$ptr, GPR:$old, GPR:$new), NoItinerary,
1725       "${:comment} ATOMIC_CMP_SWAP_I16 PSEUDO!",
1726       [(set GPR:$dst, (atomic_cmp_swap_16 GPR:$ptr, GPR:$old, GPR:$new))]>;
1727     def ATOMIC_CMP_SWAP_I32 : PseudoInst<
1728       (outs GPR:$dst), (ins GPR:$ptr, GPR:$old, GPR:$new), NoItinerary,
1729       "${:comment} ATOMIC_CMP_SWAP_I32 PSEUDO!",
1730       [(set GPR:$dst, (atomic_cmp_swap_32 GPR:$ptr, GPR:$old, GPR:$new))]>;
1731 }
1732 }
1733
1734 let mayLoad = 1 in {
1735 def LDREXB : AIldrex<0b10, (outs GPR:$dest), (ins GPR:$ptr), NoItinerary,
1736                     "ldrexb", "\t$dest, [$ptr]",
1737                     []>;
1738 def LDREXH : AIldrex<0b11, (outs GPR:$dest), (ins GPR:$ptr), NoItinerary,
1739                     "ldrexh", "\t$dest, [$ptr]",
1740                     []>;
1741 def LDREX  : AIldrex<0b00, (outs GPR:$dest), (ins GPR:$ptr), NoItinerary,
1742                     "ldrex", "\t$dest, [$ptr]",
1743                     []>;
1744 def LDREXD : AIldrex<0b01, (outs GPR:$dest, GPR:$dest2), (ins GPR:$ptr),
1745                     NoItinerary,
1746                     "ldrexd", "\t$dest, $dest2, [$ptr]",
1747                     []>;
1748 }
1749
1750 let mayStore = 1, Constraints = "@earlyclobber $success" in {
1751 def STREXB : AIstrex<0b10, (outs GPR:$success), (ins GPR:$src, GPR:$ptr),
1752                     NoItinerary,
1753                     "strexb", "\t$success, $src, [$ptr]",
1754                     []>;
1755 def STREXH : AIstrex<0b11, (outs GPR:$success), (ins GPR:$src, GPR:$ptr),
1756                     NoItinerary,
1757                     "strexh", "\t$success, $src, [$ptr]",
1758                     []>;
1759 def STREX  : AIstrex<0b00, (outs GPR:$success), (ins GPR:$src, GPR:$ptr),
1760                     NoItinerary,
1761                     "strex", "\t$success, $src, [$ptr]",
1762                     []>;
1763 def STREXD : AIstrex<0b01, (outs GPR:$success),
1764                     (ins GPR:$src, GPR:$src2, GPR:$ptr),
1765                     NoItinerary,
1766                     "strexd", "\t$success, $src, $src2, [$ptr]",
1767                     []>;
1768 }
1769
1770 //===----------------------------------------------------------------------===//
1771 // TLS Instructions
1772 //
1773
1774 // __aeabi_read_tp preserves the registers r1-r3.
1775 let isCall = 1,
1776   Defs = [R0, R12, LR, CPSR] in {
1777   def TPsoft : ABXI<0b1011, (outs), (ins), IIC_Br,
1778                "bl\t__aeabi_read_tp",
1779                [(set R0, ARMthread_pointer)]>;
1780 }
1781
1782 //===----------------------------------------------------------------------===//
1783 // SJLJ Exception handling intrinsics
1784 //   eh_sjlj_setjmp() is an instruction sequence to store the return
1785 //   address and save #0 in R0 for the non-longjmp case.
1786 //   Since by its nature we may be coming from some other function to get
1787 //   here, and we're using the stack frame for the containing function to
1788 //   save/restore registers, we can't keep anything live in regs across
1789 //   the eh_sjlj_setjmp(), else it will almost certainly have been tromped upon
1790 //   when we get here from a longjmp(). We force everthing out of registers
1791 //   except for our own input by listing the relevant registers in Defs. By
1792 //   doing so, we also cause the prologue/epilogue code to actively preserve
1793 //   all of the callee-saved resgisters, which is exactly what we want.
1794 let Defs = 
1795   [ R0,  R1,  R2,  R3,  R4,  R5,  R6,  R7,  R8,  R9,  R10, R11, R12, LR,  D0,
1796     D1,  D2,  D3,  D4,  D5,  D6,  D7,  D8,  D9,  D10, D11, D12, D13, D14, D15,
1797     D16, D17, D18, D19, D20, D21, D22, D23, D24, D25, D26, D27, D28, D29, D30,
1798     D31 ] in {
1799   def Int_eh_sjlj_setjmp : XI<(outs), (ins GPR:$src),
1800                                AddrModeNone, SizeSpecial, IndexModeNone,
1801                                Pseudo, NoItinerary,
1802                                "str\tsp, [$src, #+8] @ eh_setjmp begin\n\t"
1803                                "add\tr12, pc, #8\n\t"
1804                                "str\tr12, [$src, #+4]\n\t"
1805                                "mov\tr0, #0\n\t"
1806                                "add\tpc, pc, #0\n\t"
1807                                "mov\tr0, #1 @ eh_setjmp end", "",
1808                                [(set R0, (ARMeh_sjlj_setjmp GPR:$src))]>;
1809 }
1810
1811 //===----------------------------------------------------------------------===//
1812 // Non-Instruction Patterns
1813 //
1814
1815 // Large immediate handling.
1816
1817 // Two piece so_imms.
1818 let isReMaterializable = 1 in
1819 def MOVi2pieces : AI1x2<(outs GPR:$dst), (ins so_imm2part:$src), 
1820                          Pseudo, IIC_iMOVi,
1821                          "mov", "\t$dst, $src",
1822                          [(set GPR:$dst, so_imm2part:$src)]>,
1823                   Requires<[IsARM, NoV6T2]>;
1824
1825 def : ARMPat<(or GPR:$LHS, so_imm2part:$RHS),
1826              (ORRri (ORRri GPR:$LHS, (so_imm2part_1 imm:$RHS)),
1827                     (so_imm2part_2 imm:$RHS))>;
1828 def : ARMPat<(xor GPR:$LHS, so_imm2part:$RHS),
1829              (EORri (EORri GPR:$LHS, (so_imm2part_1 imm:$RHS)),
1830                     (so_imm2part_2 imm:$RHS))>;
1831 def : ARMPat<(add GPR:$LHS, so_imm2part:$RHS),
1832              (ADDri (ADDri GPR:$LHS, (so_imm2part_1 imm:$RHS)),
1833                     (so_imm2part_2 imm:$RHS))>;
1834 def : ARMPat<(add GPR:$LHS, so_neg_imm2part:$RHS),
1835              (SUBri (SUBri GPR:$LHS, (so_neg_imm2part_1 imm:$RHS)),
1836                     (so_neg_imm2part_2 imm:$RHS))>;
1837
1838 // 32-bit immediate using movw + movt.
1839 // This is a single pseudo instruction, the benefit is that it can be remat'd
1840 // as a single unit instead of having to handle reg inputs.
1841 // FIXME: Remove this when we can do generalized remat.
1842 let isReMaterializable = 1 in
1843 def MOVi32imm : AI1x2<(outs GPR:$dst), (ins i32imm:$src), Pseudo, IIC_iMOVi,
1844                     "movw", "\t$dst, ${src:lo16}\n\tmovt${p}\t$dst, ${src:hi16}",
1845                      [(set GPR:$dst, (i32 imm:$src))]>,
1846                Requires<[IsARM, HasV6T2]>;
1847
1848 // ConstantPool, GlobalAddress, and JumpTable
1849 def : ARMPat<(ARMWrapper  tglobaladdr :$dst), (LEApcrel tglobaladdr :$dst)>,
1850             Requires<[IsARM, DontUseMovt]>;
1851 def : ARMPat<(ARMWrapper  tconstpool  :$dst), (LEApcrel tconstpool  :$dst)>;
1852 def : ARMPat<(ARMWrapper  tglobaladdr :$dst), (MOVi32imm tglobaladdr :$dst)>,
1853             Requires<[IsARM, UseMovt]>;
1854 def : ARMPat<(ARMWrapperJT tjumptable:$dst, imm:$id),
1855              (LEApcrelJT tjumptable:$dst, imm:$id)>;
1856
1857 // TODO: add,sub,and, 3-instr forms?
1858
1859
1860 // Direct calls
1861 def : ARMPat<(ARMcall texternalsym:$func), (BL texternalsym:$func)>,
1862       Requires<[IsARM, IsNotDarwin]>;
1863 def : ARMPat<(ARMcall texternalsym:$func), (BLr9 texternalsym:$func)>,
1864       Requires<[IsARM, IsDarwin]>;
1865
1866 // zextload i1 -> zextload i8
1867 def : ARMPat<(zextloadi1 addrmode2:$addr),  (LDRB addrmode2:$addr)>;
1868
1869 // extload -> zextload
1870 def : ARMPat<(extloadi1  addrmode2:$addr),  (LDRB addrmode2:$addr)>;
1871 def : ARMPat<(extloadi8  addrmode2:$addr),  (LDRB addrmode2:$addr)>;
1872 def : ARMPat<(extloadi16 addrmode3:$addr),  (LDRH addrmode3:$addr)>;
1873
1874 def : ARMPat<(extloadi8  addrmodepc:$addr), (PICLDRB addrmodepc:$addr)>;
1875 def : ARMPat<(extloadi16 addrmodepc:$addr), (PICLDRH addrmodepc:$addr)>;
1876
1877 // smul* and smla*
1878 def : ARMV5TEPat<(mul (sra (shl GPR:$a, (i32 16)), (i32 16)),
1879                       (sra (shl GPR:$b, (i32 16)), (i32 16))),
1880                  (SMULBB GPR:$a, GPR:$b)>;
1881 def : ARMV5TEPat<(mul sext_16_node:$a, sext_16_node:$b),
1882                  (SMULBB GPR:$a, GPR:$b)>;
1883 def : ARMV5TEPat<(mul (sra (shl GPR:$a, (i32 16)), (i32 16)),
1884                       (sra GPR:$b, (i32 16))),
1885                  (SMULBT GPR:$a, GPR:$b)>;
1886 def : ARMV5TEPat<(mul sext_16_node:$a, (sra GPR:$b, (i32 16))),
1887                  (SMULBT GPR:$a, GPR:$b)>;
1888 def : ARMV5TEPat<(mul (sra GPR:$a, (i32 16)),
1889                       (sra (shl GPR:$b, (i32 16)), (i32 16))),
1890                  (SMULTB GPR:$a, GPR:$b)>;
1891 def : ARMV5TEPat<(mul (sra GPR:$a, (i32 16)), sext_16_node:$b),
1892                 (SMULTB GPR:$a, GPR:$b)>;
1893 def : ARMV5TEPat<(sra (mul GPR:$a, (sra (shl GPR:$b, (i32 16)), (i32 16))),
1894                       (i32 16)),
1895                  (SMULWB GPR:$a, GPR:$b)>;
1896 def : ARMV5TEPat<(sra (mul GPR:$a, sext_16_node:$b), (i32 16)),
1897                  (SMULWB GPR:$a, GPR:$b)>;
1898
1899 def : ARMV5TEPat<(add GPR:$acc,
1900                       (mul (sra (shl GPR:$a, (i32 16)), (i32 16)),
1901                            (sra (shl GPR:$b, (i32 16)), (i32 16)))),
1902                  (SMLABB GPR:$a, GPR:$b, GPR:$acc)>;
1903 def : ARMV5TEPat<(add GPR:$acc,
1904                       (mul sext_16_node:$a, sext_16_node:$b)),
1905                  (SMLABB GPR:$a, GPR:$b, GPR:$acc)>;
1906 def : ARMV5TEPat<(add GPR:$acc,
1907                       (mul (sra (shl GPR:$a, (i32 16)), (i32 16)),
1908                            (sra GPR:$b, (i32 16)))),
1909                  (SMLABT GPR:$a, GPR:$b, GPR:$acc)>;
1910 def : ARMV5TEPat<(add GPR:$acc,
1911                       (mul sext_16_node:$a, (sra GPR:$b, (i32 16)))),
1912                  (SMLABT GPR:$a, GPR:$b, GPR:$acc)>;
1913 def : ARMV5TEPat<(add GPR:$acc,
1914                       (mul (sra GPR:$a, (i32 16)),
1915                            (sra (shl GPR:$b, (i32 16)), (i32 16)))),
1916                  (SMLATB GPR:$a, GPR:$b, GPR:$acc)>;
1917 def : ARMV5TEPat<(add GPR:$acc,
1918                       (mul (sra GPR:$a, (i32 16)), sext_16_node:$b)),
1919                  (SMLATB GPR:$a, GPR:$b, GPR:$acc)>;
1920 def : ARMV5TEPat<(add GPR:$acc,
1921                       (sra (mul GPR:$a, (sra (shl GPR:$b, (i32 16)), (i32 16))),
1922                            (i32 16))),
1923                  (SMLAWB GPR:$a, GPR:$b, GPR:$acc)>;
1924 def : ARMV5TEPat<(add GPR:$acc,
1925                       (sra (mul GPR:$a, sext_16_node:$b), (i32 16))),
1926                  (SMLAWB GPR:$a, GPR:$b, GPR:$acc)>;
1927
1928 //===----------------------------------------------------------------------===//
1929 // Thumb Support
1930 //
1931
1932 include "ARMInstrThumb.td"
1933
1934 //===----------------------------------------------------------------------===//
1935 // Thumb2 Support
1936 //
1937
1938 include "ARMInstrThumb2.td"
1939
1940 //===----------------------------------------------------------------------===//
1941 // Floating Point Support
1942 //
1943
1944 include "ARMInstrVFP.td"
1945
1946 //===----------------------------------------------------------------------===//
1947 // Advanced SIMD (NEON) Support
1948 //
1949
1950 include "ARMInstrNEON.td"