Some single-precision VFP instructions can execute in either the VPF or Neon
[oota-llvm.git] / lib / Target / ARM / ARMInstrVFP.td
1 //===- ARMInstrVFP.td - VFP support for ARM ----------------*- 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 VFP instruction set.
11 //
12 //===----------------------------------------------------------------------===//
13
14 def SDT_FTOI    : SDTypeProfile<1, 1, [SDTCisVT<0, f32>, SDTCisFP<1>]>;
15 def SDT_ITOF    : SDTypeProfile<1, 1, [SDTCisFP<0>, SDTCisVT<1, f32>]>;
16 def SDT_CMPFP0  : SDTypeProfile<0, 1, [SDTCisFP<0>]>;
17 def SDT_VMOVDRR : SDTypeProfile<1, 2, [SDTCisVT<0, f64>, SDTCisVT<1, i32>,
18                                        SDTCisSameAs<1, 2>]>;
19
20 def arm_ftoui  : SDNode<"ARMISD::FTOUI",   SDT_FTOI>;
21 def arm_ftosi  : SDNode<"ARMISD::FTOSI",   SDT_FTOI>;
22 def arm_sitof  : SDNode<"ARMISD::SITOF",   SDT_ITOF>;
23 def arm_uitof  : SDNode<"ARMISD::UITOF",   SDT_ITOF>;
24 def arm_fmstat : SDNode<"ARMISD::FMSTAT",  SDTNone, [SDNPInGlue, SDNPOutGlue]>;
25 def arm_cmpfp  : SDNode<"ARMISD::CMPFP",   SDT_ARMCmp, [SDNPOutGlue]>;
26 def arm_cmpfp0 : SDNode<"ARMISD::CMPFPw0", SDT_CMPFP0, [SDNPOutGlue]>;
27 def arm_fmdrr  : SDNode<"ARMISD::VMOVDRR", SDT_VMOVDRR>;
28
29
30 //===----------------------------------------------------------------------===//
31 // Operand Definitions.
32 //
33
34 def vfp_f32imm : Operand<f32>,
35                  PatLeaf<(f32 fpimm), [{
36       return ARM::getVFPf32Imm(N->getValueAPF()) != -1;
37     }]> {
38   let PrintMethod = "printVFPf32ImmOperand";
39 }
40
41 def vfp_f64imm : Operand<f64>,
42                  PatLeaf<(f64 fpimm), [{
43       return ARM::getVFPf64Imm(N->getValueAPF()) != -1;
44     }]> {
45   let PrintMethod = "printVFPf64ImmOperand";
46 }
47
48
49 //===----------------------------------------------------------------------===//
50 //  Load / store Instructions.
51 //
52
53 let canFoldAsLoad = 1, isReMaterializable = 1 in {
54
55 def VLDRD : ADI5<0b1101, 0b01, (outs DPR:$Dd), (ins addrmode5:$addr),
56                  IIC_fpLoad64, "vldr", ".64\t$Dd, $addr",
57                  [(set DPR:$Dd, (f64 (load addrmode5:$addr)))]>;
58
59 def VLDRS : ASI5<0b1101, 0b01, (outs SPR:$Sd), (ins addrmode5:$addr),
60                  IIC_fpLoad32, "vldr", ".32\t$Sd, $addr",
61                  [(set SPR:$Sd, (load addrmode5:$addr))]> {
62   // Some single precision VFP instructions may be executed on both NEON and VFP
63   // pipelines.
64   let D = VFPNeonDomain;
65 }
66
67 } // End of 'let canFoldAsLoad = 1, isReMaterializable = 1 in'
68
69 def VSTRD : ADI5<0b1101, 0b00, (outs), (ins DPR:$Dd, addrmode5:$addr),
70                  IIC_fpStore64, "vstr", ".64\t$Dd, $addr",
71                  [(store (f64 DPR:$Dd), addrmode5:$addr)]>;
72
73 def VSTRS : ASI5<0b1101, 0b00, (outs), (ins SPR:$Sd, addrmode5:$addr),
74                  IIC_fpStore32, "vstr", ".32\t$Sd, $addr",
75                  [(store SPR:$Sd, addrmode5:$addr)]> {
76   // Some single precision VFP instructions may be executed on both NEON and VFP
77   // pipelines.
78   let D = VFPNeonDomain;
79 }
80
81 //===----------------------------------------------------------------------===//
82 //  Load / store multiple Instructions.
83 //
84
85 multiclass vfp_ldst_mult<string asm, bit L_bit,
86                          InstrItinClass itin, InstrItinClass itin_upd> {
87   // Double Precision
88   def DIA :
89     AXDI4<(outs), (ins GPR:$Rn, pred:$p, dpr_reglist:$regs, variable_ops),
90           IndexModeNone, itin,
91           !strconcat(asm, "ia${p}\t$Rn, $regs"), "", []> {
92     let Inst{24-23} = 0b01;       // Increment After
93     let Inst{21}    = 0;          // No writeback
94     let Inst{20}    = L_bit;
95   }
96   def DIA_UPD :
97     AXDI4<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, dpr_reglist:$regs, variable_ops),
98           IndexModeUpd, itin_upd,
99           !strconcat(asm, "ia${p}\t$Rn!, $regs"), "$Rn = $wb", []> {
100     let Inst{24-23} = 0b01;       // Increment After
101     let Inst{21}    = 1;          // Writeback
102     let Inst{20}    = L_bit;
103   }
104   def DDB_UPD :
105     AXDI4<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, dpr_reglist:$regs, variable_ops),
106           IndexModeUpd, itin_upd,
107           !strconcat(asm, "db${p}\t$Rn!, $regs"), "$Rn = $wb", []> {
108     let Inst{24-23} = 0b10;       // Decrement Before
109     let Inst{21}    = 1;          // Writeback
110     let Inst{20}    = L_bit;
111   }
112
113   // Single Precision
114   def SIA :
115     AXSI4<(outs), (ins GPR:$Rn, pred:$p, spr_reglist:$regs, variable_ops),
116           IndexModeNone, itin,
117           !strconcat(asm, "ia${p}\t$Rn, $regs"), "", []> {
118     let Inst{24-23} = 0b01;       // Increment After
119     let Inst{21}    = 0;          // No writeback
120     let Inst{20}    = L_bit;
121
122     // Some single precision VFP instructions may be executed on both NEON and
123     // VFP pipelines.
124     let D = VFPNeonDomain;
125   }
126   def SIA_UPD :
127     AXSI4<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, spr_reglist:$regs, variable_ops),
128           IndexModeUpd, itin_upd,
129           !strconcat(asm, "ia${p}\t$Rn!, $regs"), "$Rn = $wb", []> {
130     let Inst{24-23} = 0b01;       // Increment After
131     let Inst{21}    = 1;          // Writeback
132     let Inst{20}    = L_bit;
133
134     // Some single precision VFP instructions may be executed on both NEON and
135     // VFP pipelines.
136     let D = VFPNeonDomain;
137   }
138   def SDB_UPD :
139     AXSI4<(outs GPR:$wb), (ins GPR:$Rn, pred:$p, spr_reglist:$regs, variable_ops),
140           IndexModeUpd, itin_upd,
141           !strconcat(asm, "db${p}\t$Rn!, $regs"), "$Rn = $wb", []> {
142     let Inst{24-23} = 0b10;       // Decrement Before
143     let Inst{21}    = 1;          // Writeback
144     let Inst{20}    = L_bit;
145
146     // Some single precision VFP instructions may be executed on both NEON and
147     // VFP pipelines.
148     let D = VFPNeonDomain;
149   }
150 }
151
152 let neverHasSideEffects = 1 in {
153
154 let mayLoad = 1, hasExtraDefRegAllocReq = 1 in
155 defm VLDM : vfp_ldst_mult<"vldm", 1, IIC_fpLoad_m, IIC_fpLoad_mu>;
156
157 let mayStore = 1, hasExtraSrcRegAllocReq = 1 in
158 defm VSTM : vfp_ldst_mult<"vstm", 0, IIC_fpLoad_m, IIC_fpLoad_mu>;
159
160 } // neverHasSideEffects
161
162 def : MnemonicAlias<"vldm", "vldmia">;
163 def : MnemonicAlias<"vstm", "vstmia">;
164
165 // FLDMX, FSTMX - mixing S/D registers for pre-armv6 cores
166
167 //===----------------------------------------------------------------------===//
168 // FP Binary Operations.
169 //
170
171 def VADDD  : ADbI<0b11100, 0b11, 0, 0,
172                   (outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
173                   IIC_fpALU64, "vadd", ".f64\t$Dd, $Dn, $Dm",
174                   [(set DPR:$Dd, (fadd DPR:$Dn, (f64 DPR:$Dm)))]>;
175
176 def VADDS  : ASbIn<0b11100, 0b11, 0, 0,
177                    (outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
178                    IIC_fpALU32, "vadd", ".f32\t$Sd, $Sn, $Sm",
179                    [(set SPR:$Sd, (fadd SPR:$Sn, SPR:$Sm))]> {
180   // Some single precision VFP instructions may be executed on both NEON and
181   // VFP pipelines on A8.
182   let D = VFPNeonA8Domain;
183 }
184
185 def VSUBD  : ADbI<0b11100, 0b11, 1, 0,
186                   (outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
187                   IIC_fpALU64, "vsub", ".f64\t$Dd, $Dn, $Dm",
188                   [(set DPR:$Dd, (fsub DPR:$Dn, (f64 DPR:$Dm)))]>;
189
190 def VSUBS  : ASbIn<0b11100, 0b11, 1, 0,
191                    (outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
192                    IIC_fpALU32, "vsub", ".f32\t$Sd, $Sn, $Sm",
193                    [(set SPR:$Sd, (fsub SPR:$Sn, SPR:$Sm))]> {
194   // Some single precision VFP instructions may be executed on both NEON and
195   // VFP pipelines on A8.
196   let D = VFPNeonA8Domain;
197 }
198
199 def VDIVD  : ADbI<0b11101, 0b00, 0, 0,
200                   (outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
201                   IIC_fpDIV64, "vdiv", ".f64\t$Dd, $Dn, $Dm",
202                   [(set DPR:$Dd, (fdiv DPR:$Dn, (f64 DPR:$Dm)))]>;
203
204 def VDIVS  : ASbI<0b11101, 0b00, 0, 0,
205                   (outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
206                   IIC_fpDIV32, "vdiv", ".f32\t$Sd, $Sn, $Sm",
207                   [(set SPR:$Sd, (fdiv SPR:$Sn, SPR:$Sm))]>;
208
209 def VMULD  : ADbI<0b11100, 0b10, 0, 0,
210                   (outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
211                   IIC_fpMUL64, "vmul", ".f64\t$Dd, $Dn, $Dm",
212                   [(set DPR:$Dd, (fmul DPR:$Dn, (f64 DPR:$Dm)))]>;
213
214 def VMULS  : ASbIn<0b11100, 0b10, 0, 0,
215                    (outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
216                    IIC_fpMUL32, "vmul", ".f32\t$Sd, $Sn, $Sm",
217                    [(set SPR:$Sd, (fmul SPR:$Sn, SPR:$Sm))]> {
218   // Some single precision VFP instructions may be executed on both NEON and
219   // VFP pipelines on A8.
220   let D = VFPNeonA8Domain;
221 }
222
223 def VNMULD : ADbI<0b11100, 0b10, 1, 0,
224                   (outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm),
225                   IIC_fpMUL64, "vnmul", ".f64\t$Dd, $Dn, $Dm",
226                   [(set DPR:$Dd, (fneg (fmul DPR:$Dn, (f64 DPR:$Dm))))]>;
227
228 def VNMULS : ASbI<0b11100, 0b10, 1, 0,
229                   (outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm),
230                   IIC_fpMUL32, "vnmul", ".f32\t$Sd, $Sn, $Sm",
231                   [(set SPR:$Sd, (fneg (fmul SPR:$Sn, SPR:$Sm)))]> {
232   // Some single precision VFP instructions may be executed on both NEON and
233   // VFP pipelines on A8.
234   let D = VFPNeonA8Domain;
235 }
236
237 // Match reassociated forms only if not sign dependent rounding.
238 def : Pat<(fmul (fneg DPR:$a), (f64 DPR:$b)),
239           (VNMULD DPR:$a, DPR:$b)>, Requires<[NoHonorSignDependentRounding]>;
240 def : Pat<(fmul (fneg SPR:$a), SPR:$b),
241           (VNMULS SPR:$a, SPR:$b)>, Requires<[NoHonorSignDependentRounding]>;
242
243 // These are encoded as unary instructions.
244 let Defs = [FPSCR] in {
245 def VCMPED : ADuI<0b11101, 0b11, 0b0100, 0b11, 0,
246                   (outs), (ins DPR:$Dd, DPR:$Dm),
247                   IIC_fpCMP64, "vcmpe", ".f64\t$Dd, $Dm",
248                   [(arm_cmpfp DPR:$Dd, (f64 DPR:$Dm))]>;
249
250 def VCMPES : ASuI<0b11101, 0b11, 0b0100, 0b11, 0,
251                   (outs), (ins SPR:$Sd, SPR:$Sm),
252                   IIC_fpCMP32, "vcmpe", ".f32\t$Sd, $Sm",
253                   [(arm_cmpfp SPR:$Sd, SPR:$Sm)]> {
254   // Some single precision VFP instructions may be executed on both NEON and
255   // VFP pipelines on A8.
256   let D = VFPNeonA8Domain;
257 }
258
259 // FIXME: Verify encoding after integrated assembler is working.
260 def VCMPD  : ADuI<0b11101, 0b11, 0b0100, 0b01, 0,
261                   (outs), (ins DPR:$Dd, DPR:$Dm),
262                   IIC_fpCMP64, "vcmp", ".f64\t$Dd, $Dm",
263                   [/* For disassembly only; pattern left blank */]>;
264
265 def VCMPS  : ASuI<0b11101, 0b11, 0b0100, 0b01, 0,
266                   (outs), (ins SPR:$Sd, SPR:$Sm),
267                   IIC_fpCMP32, "vcmp", ".f32\t$Sd, $Sm",
268                   [/* For disassembly only; pattern left blank */]> {
269   // Some single precision VFP instructions may be executed on both NEON and
270   // VFP pipelines on A8.
271   let D = VFPNeonA8Domain;
272 }
273 } // Defs = [FPSCR]
274
275 //===----------------------------------------------------------------------===//
276 // FP Unary Operations.
277 //
278
279 def VABSD  : ADuI<0b11101, 0b11, 0b0000, 0b11, 0,
280                   (outs DPR:$Dd), (ins DPR:$Dm),
281                   IIC_fpUNA64, "vabs", ".f64\t$Dd, $Dm",
282                   [(set DPR:$Dd, (fabs (f64 DPR:$Dm)))]>;
283
284 def VABSS  : ASuIn<0b11101, 0b11, 0b0000, 0b11, 0,
285                    (outs SPR:$Sd), (ins SPR:$Sm),
286                    IIC_fpUNA32, "vabs", ".f32\t$Sd, $Sm",
287                    [(set SPR:$Sd, (fabs SPR:$Sm))]> {
288   // Some single precision VFP instructions may be executed on both NEON and
289   // VFP pipelines on A8.
290   let D = VFPNeonA8Domain;
291 }
292
293 let Defs = [FPSCR] in {
294 def VCMPEZD : ADuI<0b11101, 0b11, 0b0101, 0b11, 0,
295                    (outs), (ins DPR:$Dd),
296                    IIC_fpCMP64, "vcmpe", ".f64\t$Dd, #0",
297                    [(arm_cmpfp0 (f64 DPR:$Dd))]> {
298   let Inst{3-0} = 0b0000;
299   let Inst{5}   = 0;
300 }
301
302 def VCMPEZS : ASuI<0b11101, 0b11, 0b0101, 0b11, 0,
303                    (outs), (ins SPR:$Sd),
304                    IIC_fpCMP32, "vcmpe", ".f32\t$Sd, #0",
305                    [(arm_cmpfp0 SPR:$Sd)]> {
306   let Inst{3-0} = 0b0000;
307   let Inst{5}   = 0;
308
309   // Some single precision VFP instructions may be executed on both NEON and
310   // VFP pipelines on A8.
311   let D = VFPNeonA8Domain;
312 }
313
314 // FIXME: Verify encoding after integrated assembler is working.
315 def VCMPZD  : ADuI<0b11101, 0b11, 0b0101, 0b01, 0,
316                    (outs), (ins DPR:$Dd),
317                    IIC_fpCMP64, "vcmp", ".f64\t$Dd, #0",
318                    [/* For disassembly only; pattern left blank */]> {
319   let Inst{3-0} = 0b0000;
320   let Inst{5}   = 0;
321 }
322
323 def VCMPZS  : ASuI<0b11101, 0b11, 0b0101, 0b01, 0,
324                    (outs), (ins SPR:$Sd),
325                    IIC_fpCMP32, "vcmp", ".f32\t$Sd, #0",
326                    [/* For disassembly only; pattern left blank */]> {
327   let Inst{3-0} = 0b0000;
328   let Inst{5}   = 0;
329
330   // Some single precision VFP instructions may be executed on both NEON and
331   // VFP pipelines on A8.
332   let D = VFPNeonA8Domain;
333 }
334 } // Defs = [FPSCR]
335
336 def VCVTDS  : ASuI<0b11101, 0b11, 0b0111, 0b11, 0,
337                    (outs DPR:$Dd), (ins SPR:$Sm),
338                    IIC_fpCVTDS, "vcvt", ".f64.f32\t$Dd, $Sm",
339                    [(set DPR:$Dd, (fextend SPR:$Sm))]> {
340   // Instruction operands.
341   bits<5> Dd;
342   bits<5> Sm;
343
344   // Encode instruction operands.
345   let Inst{3-0}   = Sm{4-1};
346   let Inst{5}     = Sm{0};
347   let Inst{15-12} = Dd{3-0};
348   let Inst{22}    = Dd{4};
349 }
350
351 // Special case encoding: bits 11-8 is 0b1011.
352 def VCVTSD  : VFPAI<(outs SPR:$Sd), (ins DPR:$Dm), VFPUnaryFrm,
353                     IIC_fpCVTSD, "vcvt", ".f32.f64\t$Sd, $Dm",
354                     [(set SPR:$Sd, (fround DPR:$Dm))]> {
355   // Instruction operands.
356   bits<5> Sd;
357   bits<5> Dm;
358
359   // Encode instruction operands.
360   let Inst{3-0}   = Dm{3-0};
361   let Inst{5}     = Dm{4};
362   let Inst{15-12} = Sd{4-1};
363   let Inst{22}    = Sd{0};
364
365   let Inst{27-23} = 0b11101;
366   let Inst{21-16} = 0b110111;
367   let Inst{11-8}  = 0b1011;
368   let Inst{7-6}   = 0b11;
369   let Inst{4}     = 0;
370 }
371
372 // Between half-precision and single-precision.  For disassembly only.
373
374 // FIXME: Verify encoding after integrated assembler is working.
375 def VCVTBSH: ASuI<0b11101, 0b11, 0b0010, 0b01, 0, (outs SPR:$dst), (ins SPR:$a),
376                  /* FIXME */ IIC_fpCVTSH, "vcvtb", ".f32.f16\t$dst, $a",
377                  [/* For disassembly only; pattern left blank */]>;
378
379 def : ARMPat<(f32_to_f16 SPR:$a),
380              (i32 (COPY_TO_REGCLASS (VCVTBSH SPR:$a), GPR))>;
381
382 def VCVTBHS: ASuI<0b11101, 0b11, 0b0011, 0b01, 0, (outs SPR:$dst), (ins SPR:$a),
383                  /* FIXME */ IIC_fpCVTHS, "vcvtb", ".f16.f32\t$dst, $a",
384                  [/* For disassembly only; pattern left blank */]>;
385
386 def : ARMPat<(f16_to_f32 GPR:$a),
387              (VCVTBHS (COPY_TO_REGCLASS GPR:$a, SPR))>;
388
389 def VCVTTSH: ASuI<0b11101, 0b11, 0b0010, 0b11, 0, (outs SPR:$dst), (ins SPR:$a),
390                  /* FIXME */ IIC_fpCVTSH, "vcvtt", ".f32.f16\t$dst, $a",
391                  [/* For disassembly only; pattern left blank */]>;
392
393 def VCVTTHS: ASuI<0b11101, 0b11, 0b0011, 0b11, 0, (outs SPR:$dst), (ins SPR:$a),
394                  /* FIXME */ IIC_fpCVTHS, "vcvtt", ".f16.f32\t$dst, $a",
395                  [/* For disassembly only; pattern left blank */]>;
396
397 def VNEGD  : ADuI<0b11101, 0b11, 0b0001, 0b01, 0,
398                   (outs DPR:$Dd), (ins DPR:$Dm),
399                   IIC_fpUNA64, "vneg", ".f64\t$Dd, $Dm",
400                   [(set DPR:$Dd, (fneg (f64 DPR:$Dm)))]>;
401
402 def VNEGS  : ASuIn<0b11101, 0b11, 0b0001, 0b01, 0,
403                    (outs SPR:$Sd), (ins SPR:$Sm),
404                    IIC_fpUNA32, "vneg", ".f32\t$Sd, $Sm",
405                    [(set SPR:$Sd, (fneg SPR:$Sm))]> {
406   // Some single precision VFP instructions may be executed on both NEON and
407   // VFP pipelines on A8.
408   let D = VFPNeonA8Domain;
409 }
410
411 def VSQRTD : ADuI<0b11101, 0b11, 0b0001, 0b11, 0,
412                   (outs DPR:$Dd), (ins DPR:$Dm),
413                   IIC_fpSQRT64, "vsqrt", ".f64\t$Dd, $Dm",
414                   [(set DPR:$Dd, (fsqrt (f64 DPR:$Dm)))]>;
415
416 def VSQRTS : ASuI<0b11101, 0b11, 0b0001, 0b11, 0,
417                   (outs SPR:$Sd), (ins SPR:$Sm),
418                   IIC_fpSQRT32, "vsqrt", ".f32\t$Sd, $Sm",
419                   [(set SPR:$Sd, (fsqrt SPR:$Sm))]>;
420
421 let neverHasSideEffects = 1 in {
422 def VMOVD  : ADuI<0b11101, 0b11, 0b0000, 0b01, 0,
423                   (outs DPR:$Dd), (ins DPR:$Dm),
424                   IIC_fpUNA64, "vmov", ".f64\t$Dd, $Dm", []>;
425
426 def VMOVS  : ASuI<0b11101, 0b11, 0b0000, 0b01, 0,
427                   (outs SPR:$Sd), (ins SPR:$Sm),
428                   IIC_fpUNA32, "vmov", ".f32\t$Sd, $Sm", []>;
429 } // neverHasSideEffects
430
431 //===----------------------------------------------------------------------===//
432 // FP <-> GPR Copies.  Int <-> FP Conversions.
433 //
434
435 def VMOVRS : AVConv2I<0b11100001, 0b1010,
436                       (outs GPR:$Rt), (ins SPR:$Sn),
437                       IIC_fpMOVSI, "vmov", "\t$Rt, $Sn",
438                       [(set GPR:$Rt, (bitconvert SPR:$Sn))]> {
439   // Instruction operands.
440   bits<4> Rt;
441   bits<5> Sn;
442
443   // Encode instruction operands.
444   let Inst{19-16} = Sn{4-1};
445   let Inst{7}     = Sn{0};
446   let Inst{15-12} = Rt;
447
448   let Inst{6-5}   = 0b00;
449   let Inst{3-0}   = 0b0000;
450
451   // Some single precision VFP instructions may be executed on both NEON and VFP
452   // pipelines.
453   let D = VFPNeonDomain;
454 }
455
456 def VMOVSR : AVConv4I<0b11100000, 0b1010,
457                       (outs SPR:$Sn), (ins GPR:$Rt),
458                       IIC_fpMOVIS, "vmov", "\t$Sn, $Rt",
459                       [(set SPR:$Sn, (bitconvert GPR:$Rt))]> {
460   // Instruction operands.
461   bits<5> Sn;
462   bits<4> Rt;
463
464   // Encode instruction operands.
465   let Inst{19-16} = Sn{4-1};
466   let Inst{7}     = Sn{0};
467   let Inst{15-12} = Rt;
468
469   let Inst{6-5}   = 0b00;
470   let Inst{3-0}   = 0b0000;
471
472   // Some single precision VFP instructions may be executed on both NEON and VFP
473   // pipelines.
474   let D = VFPNeonDomain;
475 }
476
477 let neverHasSideEffects = 1 in {
478 def VMOVRRD  : AVConv3I<0b11000101, 0b1011,
479                         (outs GPR:$Rt, GPR:$Rt2), (ins DPR:$Dm),
480                         IIC_fpMOVDI, "vmov", "\t$Rt, $Rt2, $Dm",
481                  [/* FIXME: Can't write pattern for multiple result instr*/]> {
482   // Instruction operands.
483   bits<5> Dm;
484   bits<4> Rt;
485   bits<4> Rt2;
486
487   // Encode instruction operands.
488   let Inst{3-0}   = Dm{3-0};
489   let Inst{5}     = Dm{4};
490   let Inst{15-12} = Rt;
491   let Inst{19-16} = Rt2;
492
493   let Inst{7-6} = 0b00;
494
495   // Some single precision VFP instructions may be executed on both NEON and VFP
496   // pipelines.
497   let D = VFPNeonDomain;
498 }
499
500 def VMOVRRS  : AVConv3I<0b11000101, 0b1010,
501                       (outs GPR:$wb, GPR:$dst2), (ins SPR:$src1, SPR:$src2),
502                  IIC_fpMOVDI, "vmov", "\t$wb, $dst2, $src1, $src2",
503                  [/* For disassembly only; pattern left blank */]> {
504   let Inst{7-6} = 0b00;
505
506   // Some single precision VFP instructions may be executed on both NEON and VFP
507   // pipelines.
508   let D = VFPNeonDomain;
509 }
510 } // neverHasSideEffects
511
512 // FMDHR: GPR -> SPR
513 // FMDLR: GPR -> SPR
514
515 def VMOVDRR : AVConv5I<0b11000100, 0b1011,
516                       (outs DPR:$Dm), (ins GPR:$Rt, GPR:$Rt2),
517                       IIC_fpMOVID, "vmov", "\t$Dm, $Rt, $Rt2",
518                       [(set DPR:$Dm, (arm_fmdrr GPR:$Rt, GPR:$Rt2))]> {
519   // Instruction operands.
520   bits<5> Dm;
521   bits<4> Rt;
522   bits<4> Rt2;
523
524   // Encode instruction operands.
525   let Inst{3-0}   = Dm{3-0};
526   let Inst{5}     = Dm{4};
527   let Inst{15-12} = Rt;
528   let Inst{19-16} = Rt2;
529
530   let Inst{7-6}   = 0b00;
531
532   // Some single precision VFP instructions may be executed on both NEON and VFP
533   // pipelines.
534   let D = VFPNeonDomain;
535 }
536
537 let neverHasSideEffects = 1 in
538 def VMOVSRR : AVConv5I<0b11000100, 0b1010,
539                      (outs SPR:$dst1, SPR:$dst2), (ins GPR:$src1, GPR:$src2),
540                 IIC_fpMOVID, "vmov", "\t$dst1, $dst2, $src1, $src2",
541                 [/* For disassembly only; pattern left blank */]> {
542   let Inst{7-6} = 0b00;
543
544   // Some single precision VFP instructions may be executed on both NEON and VFP
545   // pipelines.
546   let D = VFPNeonDomain;
547 }
548
549 // FMRDH: SPR -> GPR
550 // FMRDL: SPR -> GPR
551 // FMRRS: SPR -> GPR
552 // FMRX:  SPR system reg -> GPR
553 // FMSRR: GPR -> SPR
554 // FMXR:  GPR -> VFP system reg
555
556
557 // Int -> FP:
558
559 class AVConv1IDs_Encode<bits<5> opcod1, bits<2> opcod2, bits<4> opcod3,
560                         bits<4> opcod4, dag oops, dag iops,
561                         InstrItinClass itin, string opc, string asm,
562                         list<dag> pattern>
563   : AVConv1I<opcod1, opcod2, opcod3, opcod4, oops, iops, itin, opc, asm,
564              pattern> {
565   // Instruction operands.
566   bits<5> Dd;
567   bits<5> Sm;
568
569   // Encode instruction operands.
570   let Inst{3-0}   = Sm{4-1};
571   let Inst{5}     = Sm{0};
572   let Inst{15-12} = Dd{3-0};
573   let Inst{22}    = Dd{4};
574 }
575
576 class AVConv1InSs_Encode<bits<5> opcod1, bits<2> opcod2, bits<4> opcod3,
577                          bits<4> opcod4, dag oops, dag iops,InstrItinClass itin,
578                          string opc, string asm, list<dag> pattern>
579   : AVConv1In<opcod1, opcod2, opcod3, opcod4, oops, iops, itin, opc, asm,
580               pattern> {
581   // Instruction operands.
582   bits<5> Sd;
583   bits<5> Sm;
584
585   // Encode instruction operands.
586   let Inst{3-0}   = Sm{4-1};
587   let Inst{5}     = Sm{0};
588   let Inst{15-12} = Sd{4-1};
589   let Inst{22}    = Sd{0};
590 }
591
592 def VSITOD : AVConv1IDs_Encode<0b11101, 0b11, 0b1000, 0b1011,
593                                (outs DPR:$Dd), (ins SPR:$Sm),
594                                IIC_fpCVTID, "vcvt", ".f64.s32\t$Dd, $Sm",
595                                [(set DPR:$Dd, (f64 (arm_sitof SPR:$Sm)))]> {
596   let Inst{7} = 1; // s32
597 }
598
599 def VSITOS : AVConv1InSs_Encode<0b11101, 0b11, 0b1000, 0b1010,
600                                 (outs SPR:$Sd),(ins SPR:$Sm),
601                                 IIC_fpCVTIS, "vcvt", ".f32.s32\t$Sd, $Sm",
602                                 [(set SPR:$Sd, (arm_sitof SPR:$Sm))]> {
603   let Inst{7} = 1; // s32
604
605   // Some single precision VFP instructions may be executed on both NEON and
606   // VFP pipelines on A8.
607   let D = VFPNeonA8Domain;
608 }
609
610 def VUITOD : AVConv1IDs_Encode<0b11101, 0b11, 0b1000, 0b1011,
611                                (outs DPR:$Dd), (ins SPR:$Sm),
612                                IIC_fpCVTID, "vcvt", ".f64.u32\t$Dd, $Sm",
613                                [(set DPR:$Dd, (f64 (arm_uitof SPR:$Sm)))]> {
614   let Inst{7} = 0; // u32
615 }
616
617 def VUITOS : AVConv1InSs_Encode<0b11101, 0b11, 0b1000, 0b1010,
618                                 (outs SPR:$Sd), (ins SPR:$Sm),
619                                 IIC_fpCVTIS, "vcvt", ".f32.u32\t$Sd, $Sm",
620                                 [(set SPR:$Sd, (arm_uitof SPR:$Sm))]> {
621   let Inst{7} = 0; // u32
622
623   // Some single precision VFP instructions may be executed on both NEON and
624   // VFP pipelines on A8.
625   let D = VFPNeonA8Domain;
626 }
627
628 // FP -> Int:
629
630 class AVConv1IsD_Encode<bits<5> opcod1, bits<2> opcod2, bits<4> opcod3,
631                         bits<4> opcod4, dag oops, dag iops,
632                         InstrItinClass itin, string opc, string asm,
633                         list<dag> pattern>
634   : AVConv1I<opcod1, opcod2, opcod3, opcod4, oops, iops, itin, opc, asm,
635              pattern> {
636   // Instruction operands.
637   bits<5> Sd;
638   bits<5> Dm;
639
640   // Encode instruction operands.
641   let Inst{3-0}   = Dm{3-0};
642   let Inst{5}     = Dm{4};
643   let Inst{15-12} = Sd{4-1};
644   let Inst{22}    = Sd{0};
645 }
646
647 class AVConv1InsS_Encode<bits<5> opcod1, bits<2> opcod2, bits<4> opcod3,
648                          bits<4> opcod4, dag oops, dag iops,
649                          InstrItinClass itin, string opc, string asm,
650                          list<dag> pattern>
651   : AVConv1In<opcod1, opcod2, opcod3, opcod4, oops, iops, itin, opc, asm,
652               pattern> {
653   // Instruction operands.
654   bits<5> Sd;
655   bits<5> Sm;
656
657   // Encode instruction operands.
658   let Inst{3-0}   = Sm{4-1};
659   let Inst{5}     = Sm{0};
660   let Inst{15-12} = Sd{4-1};
661   let Inst{22}    = Sd{0};
662 }
663
664 // Always set Z bit in the instruction, i.e. "round towards zero" variants.
665 def VTOSIZD : AVConv1IsD_Encode<0b11101, 0b11, 0b1101, 0b1011,
666                                 (outs SPR:$Sd), (ins DPR:$Dm),
667                                 IIC_fpCVTDI, "vcvt", ".s32.f64\t$Sd, $Dm",
668                                 [(set SPR:$Sd, (arm_ftosi (f64 DPR:$Dm)))]> {
669   let Inst{7} = 1; // Z bit
670 }
671
672 def VTOSIZS : AVConv1InsS_Encode<0b11101, 0b11, 0b1101, 0b1010,
673                                  (outs SPR:$Sd), (ins SPR:$Sm),
674                                  IIC_fpCVTSI, "vcvt", ".s32.f32\t$Sd, $Sm",
675                                  [(set SPR:$Sd, (arm_ftosi SPR:$Sm))]> {
676   let Inst{7} = 1; // Z bit
677
678   // Some single precision VFP instructions may be executed on both NEON and
679   // VFP pipelines on A8.
680   let D = VFPNeonA8Domain;
681 }
682
683 def VTOUIZD : AVConv1IsD_Encode<0b11101, 0b11, 0b1100, 0b1011,
684                                (outs SPR:$Sd), (ins DPR:$Dm),
685                                IIC_fpCVTDI, "vcvt", ".u32.f64\t$Sd, $Dm",
686                                [(set SPR:$Sd, (arm_ftoui (f64 DPR:$Dm)))]> {
687   let Inst{7} = 1; // Z bit
688 }
689
690 def VTOUIZS : AVConv1InsS_Encode<0b11101, 0b11, 0b1100, 0b1010,
691                                  (outs SPR:$Sd), (ins SPR:$Sm),
692                                  IIC_fpCVTSI, "vcvt", ".u32.f32\t$Sd, $Sm",
693                                  [(set SPR:$Sd, (arm_ftoui SPR:$Sm))]> {
694   let Inst{7} = 1; // Z bit
695
696   // Some single precision VFP instructions may be executed on both NEON and
697   // VFP pipelines on A8.
698   let D = VFPNeonA8Domain;
699 }
700
701 // And the Z bit '0' variants, i.e. use the rounding mode specified by FPSCR.
702 let Uses = [FPSCR] in {
703 // FIXME: Verify encoding after integrated assembler is working.
704 def VTOSIRD : AVConv1IsD_Encode<0b11101, 0b11, 0b1101, 0b1011,
705                                 (outs SPR:$Sd), (ins DPR:$Dm),
706                                 IIC_fpCVTDI, "vcvtr", ".s32.f64\t$Sd, $Dm",
707                                 [(set SPR:$Sd, (int_arm_vcvtr (f64 DPR:$Dm)))]>{
708   let Inst{7} = 0; // Z bit
709 }
710
711 def VTOSIRS : AVConv1InsS_Encode<0b11101, 0b11, 0b1101, 0b1010,
712                                  (outs SPR:$Sd), (ins SPR:$Sm),
713                                  IIC_fpCVTSI, "vcvtr", ".s32.f32\t$Sd, $Sm",
714                                  [(set SPR:$Sd, (int_arm_vcvtr SPR:$Sm))]> {
715   let Inst{7} = 0; // Z bit
716 }
717
718 def VTOUIRD : AVConv1IsD_Encode<0b11101, 0b11, 0b1100, 0b1011,
719                                 (outs SPR:$Sd), (ins DPR:$Dm),
720                                 IIC_fpCVTDI, "vcvtr", ".u32.f64\t$Sd, $Dm",
721                                 [(set SPR:$Sd, (int_arm_vcvtru(f64 DPR:$Dm)))]>{
722   let Inst{7} = 0; // Z bit
723 }
724
725 def VTOUIRS : AVConv1InsS_Encode<0b11101, 0b11, 0b1100, 0b1010,
726                                  (outs SPR:$Sd), (ins SPR:$Sm),
727                                  IIC_fpCVTSI, "vcvtr", ".u32.f32\t$Sd, $Sm",
728                                  [(set SPR:$Sd, (int_arm_vcvtru SPR:$Sm))]> {
729   let Inst{7} = 0; // Z bit
730 }
731 }
732
733 // Convert between floating-point and fixed-point
734 // Data type for fixed-point naming convention:
735 //   S16 (U=0, sx=0) -> SH
736 //   U16 (U=1, sx=0) -> UH
737 //   S32 (U=0, sx=1) -> SL
738 //   U32 (U=1, sx=1) -> UL
739
740 // FIXME: Marking these as codegen only seems wrong. They are real
741 //        instructions(?)
742 let Constraints = "$a = $dst", isCodeGenOnly = 1 in {
743
744 // FP to Fixed-Point:
745
746 def VTOSHS : AVConv1XI<0b11101, 0b11, 0b1110, 0b1010, 0,
747                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
748                  IIC_fpCVTSI, "vcvt", ".s16.f32\t$dst, $a, $fbits",
749                  [/* For disassembly only; pattern left blank */]> {
750   // Some single precision VFP instructions may be executed on both NEON and
751   // VFP pipelines on A8.
752   let D = VFPNeonA8Domain;
753 }
754
755 def VTOUHS : AVConv1XI<0b11101, 0b11, 0b1111, 0b1010, 0,
756                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
757                  IIC_fpCVTSI, "vcvt", ".u16.f32\t$dst, $a, $fbits",
758                  [/* For disassembly only; pattern left blank */]> {
759   // Some single precision VFP instructions may be executed on both NEON and
760   // VFP pipelines on A8.
761   let D = VFPNeonA8Domain;
762 }
763
764 def VTOSLS : AVConv1XI<0b11101, 0b11, 0b1110, 0b1010, 1,
765                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
766                  IIC_fpCVTSI, "vcvt", ".s32.f32\t$dst, $a, $fbits",
767                  [/* For disassembly only; pattern left blank */]> {
768   // Some single precision VFP instructions may be executed on both NEON and
769   // VFP pipelines on A8.
770   let D = VFPNeonA8Domain;
771 }
772
773 def VTOULS : AVConv1XI<0b11101, 0b11, 0b1111, 0b1010, 1,
774                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
775                  IIC_fpCVTSI, "vcvt", ".u32.f32\t$dst, $a, $fbits",
776                  [/* For disassembly only; pattern left blank */]> {
777   // Some single precision VFP instructions may be executed on both NEON and
778   // VFP pipelines on A8.
779   let D = VFPNeonA8Domain;
780 }
781
782 def VTOSHD : AVConv1XI<0b11101, 0b11, 0b1110, 0b1011, 0,
783                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
784                  IIC_fpCVTDI, "vcvt", ".s16.f64\t$dst, $a, $fbits",
785                  [/* For disassembly only; pattern left blank */]>;
786
787 def VTOUHD : AVConv1XI<0b11101, 0b11, 0b1111, 0b1011, 0,
788                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
789                  IIC_fpCVTDI, "vcvt", ".u16.f64\t$dst, $a, $fbits",
790                  [/* For disassembly only; pattern left blank */]>;
791
792 def VTOSLD : AVConv1XI<0b11101, 0b11, 0b1110, 0b1011, 1,
793                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
794                  IIC_fpCVTDI, "vcvt", ".s32.f64\t$dst, $a, $fbits",
795                  [/* For disassembly only; pattern left blank */]>;
796
797 def VTOULD : AVConv1XI<0b11101, 0b11, 0b1111, 0b1011, 1,
798                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
799                  IIC_fpCVTDI, "vcvt", ".u32.f64\t$dst, $a, $fbits",
800                  [/* For disassembly only; pattern left blank */]>;
801
802 // Fixed-Point to FP:
803
804 def VSHTOS : AVConv1XI<0b11101, 0b11, 0b1010, 0b1010, 0,
805                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
806                  IIC_fpCVTIS, "vcvt", ".f32.s16\t$dst, $a, $fbits",
807                  [/* For disassembly only; pattern left blank */]> {
808   // Some single precision VFP instructions may be executed on both NEON and
809   // VFP pipelines on A8.
810   let D = VFPNeonA8Domain;
811 }
812
813 def VUHTOS : AVConv1XI<0b11101, 0b11, 0b1011, 0b1010, 0,
814                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
815                  IIC_fpCVTIS, "vcvt", ".f32.u16\t$dst, $a, $fbits",
816                  [/* For disassembly only; pattern left blank */]> {
817   // Some single precision VFP instructions may be executed on both NEON and
818   // VFP pipelines on A8.
819   let D = VFPNeonA8Domain;
820 }
821
822 def VSLTOS : AVConv1XI<0b11101, 0b11, 0b1010, 0b1010, 1,
823                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
824                  IIC_fpCVTIS, "vcvt", ".f32.s32\t$dst, $a, $fbits",
825                  [/* For disassembly only; pattern left blank */]> {
826   // Some single precision VFP instructions may be executed on both NEON and
827   // VFP pipelines on A8.
828   let D = VFPNeonA8Domain;
829 }
830
831 def VULTOS : AVConv1XI<0b11101, 0b11, 0b1011, 0b1010, 1,
832                        (outs SPR:$dst), (ins SPR:$a, i32imm:$fbits),
833                  IIC_fpCVTIS, "vcvt", ".f32.u32\t$dst, $a, $fbits",
834                  [/* For disassembly only; pattern left blank */]> {
835   // Some single precision VFP instructions may be executed on both NEON and
836   // VFP pipelines on A8.
837   let D = VFPNeonA8Domain;
838 }
839
840 def VSHTOD : AVConv1XI<0b11101, 0b11, 0b1010, 0b1011, 0,
841                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
842                  IIC_fpCVTID, "vcvt", ".f64.s16\t$dst, $a, $fbits",
843                  [/* For disassembly only; pattern left blank */]>;
844
845 def VUHTOD : AVConv1XI<0b11101, 0b11, 0b1011, 0b1011, 0,
846                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
847                  IIC_fpCVTID, "vcvt", ".f64.u16\t$dst, $a, $fbits",
848                  [/* For disassembly only; pattern left blank */]>;
849
850 def VSLTOD : AVConv1XI<0b11101, 0b11, 0b1010, 0b1011, 1,
851                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
852                  IIC_fpCVTID, "vcvt", ".f64.s32\t$dst, $a, $fbits",
853                  [/* For disassembly only; pattern left blank */]>;
854
855 def VULTOD : AVConv1XI<0b11101, 0b11, 0b1011, 0b1011, 1,
856                        (outs DPR:$dst), (ins DPR:$a, i32imm:$fbits),
857                  IIC_fpCVTID, "vcvt", ".f64.u32\t$dst, $a, $fbits",
858                  [/* For disassembly only; pattern left blank */]>;
859
860 } // End of 'let Constraints = "$a = $dst", isCodeGenOnly = 1 in'
861
862 //===----------------------------------------------------------------------===//
863 // FP FMA Operations.
864 //
865
866 def VMLAD : ADbI<0b11100, 0b00, 0, 0,
867                  (outs DPR:$Dd), (ins DPR:$Ddin, DPR:$Dn, DPR:$Dm),
868                  IIC_fpMAC64, "vmla", ".f64\t$Dd, $Dn, $Dm",
869                  [(set DPR:$Dd, (fadd_mlx (fmul_su DPR:$Dn, DPR:$Dm),
870                                           (f64 DPR:$Ddin)))]>,
871               RegConstraint<"$Ddin = $Dd">,
872               Requires<[HasVFP2,UseFPVMLx]>;
873
874 def VMLAS : ASbIn<0b11100, 0b00, 0, 0,
875                   (outs SPR:$Sd), (ins SPR:$Sdin, SPR:$Sn, SPR:$Sm),
876                   IIC_fpMAC32, "vmla", ".f32\t$Sd, $Sn, $Sm",
877                   [(set SPR:$Sd, (fadd_mlx (fmul_su SPR:$Sn, SPR:$Sm),
878                                            SPR:$Sdin))]>,
879               RegConstraint<"$Sdin = $Sd">,
880               Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]> {
881   // Some single precision VFP instructions may be executed on both NEON and
882   // VFP pipelines on A8.
883   let D = VFPNeonA8Domain;
884 }
885
886 def : Pat<(fadd_mlx DPR:$dstin, (fmul_su DPR:$a, (f64 DPR:$b))),
887           (VMLAD DPR:$dstin, DPR:$a, DPR:$b)>,
888           Requires<[HasVFP2,UseFPVMLx]>;
889 def : Pat<(fadd_mlx SPR:$dstin, (fmul_su SPR:$a, SPR:$b)),
890           (VMLAS SPR:$dstin, SPR:$a, SPR:$b)>,
891           Requires<[HasVFP2,DontUseNEONForFP, UseFPVMLx]>;
892
893 def VMLSD : ADbI<0b11100, 0b00, 1, 0,
894                  (outs DPR:$Dd), (ins DPR:$Ddin, DPR:$Dn, DPR:$Dm),
895                  IIC_fpMAC64, "vmls", ".f64\t$Dd, $Dn, $Dm",
896                  [(set DPR:$Dd, (fadd_mlx (fneg (fmul_su DPR:$Dn,DPR:$Dm)),
897                                           (f64 DPR:$Ddin)))]>,
898               RegConstraint<"$Ddin = $Dd">,
899               Requires<[HasVFP2,UseFPVMLx]>;
900
901 def VMLSS : ASbIn<0b11100, 0b00, 1, 0,
902                   (outs SPR:$Sd), (ins SPR:$Sdin, SPR:$Sn, SPR:$Sm),
903                   IIC_fpMAC32, "vmls", ".f32\t$Sd, $Sn, $Sm",
904                   [(set SPR:$Sd, (fadd_mlx (fneg (fmul_su SPR:$Sn, SPR:$Sm)),
905                                            SPR:$Sdin))]>,
906               RegConstraint<"$Sdin = $Sd">,
907               Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]> {
908   // Some single precision VFP instructions may be executed on both NEON and
909   // VFP pipelines on A8.
910   let D = VFPNeonA8Domain;
911 }
912
913 def : Pat<(fsub_mlx DPR:$dstin, (fmul_su DPR:$a, (f64 DPR:$b))),
914           (VMLSD DPR:$dstin, DPR:$a, DPR:$b)>,
915           Requires<[HasVFP2,UseFPVMLx]>;
916 def : Pat<(fsub_mlx SPR:$dstin, (fmul_su SPR:$a, SPR:$b)),
917           (VMLSS SPR:$dstin, SPR:$a, SPR:$b)>,
918           Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]>;
919
920 def VNMLAD : ADbI<0b11100, 0b01, 1, 0,
921                   (outs DPR:$Dd), (ins DPR:$Ddin, DPR:$Dn, DPR:$Dm),
922                   IIC_fpMAC64, "vnmla", ".f64\t$Dd, $Dn, $Dm",
923                   [(set DPR:$Dd,(fsub_mlx (fneg (fmul_su DPR:$Dn,DPR:$Dm)),
924                                           (f64 DPR:$Ddin)))]>,
925                 RegConstraint<"$Ddin = $Dd">,
926                 Requires<[HasVFP2,UseFPVMLx]>;
927
928 def VNMLAS : ASbI<0b11100, 0b01, 1, 0,
929                   (outs SPR:$Sd), (ins SPR:$Sdin, SPR:$Sn, SPR:$Sm),
930                   IIC_fpMAC32, "vnmla", ".f32\t$Sd, $Sn, $Sm",
931                   [(set SPR:$Sd, (fsub_mlx (fneg (fmul_su SPR:$Sn, SPR:$Sm)),
932                                            SPR:$Sdin))]>,
933                 RegConstraint<"$Sdin = $Sd">,
934                 Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]> {
935   // Some single precision VFP instructions may be executed on both NEON and
936   // VFP pipelines on A8.
937   let D = VFPNeonA8Domain;
938 }
939
940 def : Pat<(fsub_mlx (fneg (fmul_su DPR:$a, (f64 DPR:$b))), DPR:$dstin),
941           (VNMLAD DPR:$dstin, DPR:$a, DPR:$b)>,
942           Requires<[HasVFP2,UseFPVMLx]>;
943 def : Pat<(fsub_mlx (fneg (fmul_su SPR:$a, SPR:$b)), SPR:$dstin),
944           (VNMLAS SPR:$dstin, SPR:$a, SPR:$b)>,
945           Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]>;
946
947 def VNMLSD : ADbI<0b11100, 0b01, 0, 0,
948                   (outs DPR:$Dd), (ins DPR:$Ddin, DPR:$Dn, DPR:$Dm),
949                   IIC_fpMAC64, "vnmls", ".f64\t$Dd, $Dn, $Dm",
950                   [(set DPR:$Dd, (fsub_mlx (fmul_su DPR:$Dn, DPR:$Dm),
951                                            (f64 DPR:$Ddin)))]>,
952                RegConstraint<"$Ddin = $Dd">,
953                Requires<[HasVFP2,UseFPVMLx]>;
954
955 def VNMLSS : ASbI<0b11100, 0b01, 0, 0,
956                   (outs SPR:$Sd), (ins SPR:$Sdin, SPR:$Sn, SPR:$Sm),
957                   IIC_fpMAC32, "vnmls", ".f32\t$Sd, $Sn, $Sm",
958              [(set SPR:$Sd, (fsub_mlx (fmul_su SPR:$Sn, SPR:$Sm), SPR:$Sdin))]>,
959                          RegConstraint<"$Sdin = $Sd">,
960                   Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]> {
961   // Some single precision VFP instructions may be executed on both NEON and
962   // VFP pipelines on A8.
963   let D = VFPNeonA8Domain;
964 }
965
966 def : Pat<(fsub_mlx (fmul_su DPR:$a, (f64 DPR:$b)), DPR:$dstin),
967           (VNMLSD DPR:$dstin, DPR:$a, DPR:$b)>,
968           Requires<[HasVFP2,UseFPVMLx]>;
969 def : Pat<(fsub_mlx (fmul_su SPR:$a, SPR:$b), SPR:$dstin),
970           (VNMLSS SPR:$dstin, SPR:$a, SPR:$b)>,
971           Requires<[HasVFP2,DontUseNEONForFP,UseFPVMLx]>;
972
973
974 //===----------------------------------------------------------------------===//
975 // FP Conditional moves.
976 //
977
978 let neverHasSideEffects = 1 in {
979 def VMOVDcc  : ARMPseudoInst<(outs DPR:$Dd), (ins DPR:$Dn, DPR:$Dm, pred:$p),
980                     Size4Bytes, IIC_fpUNA64,
981                     [/*(set DPR:$Dd, (ARMcmov DPR:$Dn, DPR:$Dm, imm:$cc))*/]>,
982                  RegConstraint<"$Dn = $Dd">;
983
984 def VMOVScc  : ARMPseudoInst<(outs SPR:$Sd), (ins SPR:$Sn, SPR:$Sm, pred:$p),
985                     Size4Bytes, IIC_fpUNA32,
986                     [/*(set SPR:$Sd, (ARMcmov SPR:$Sn, SPR:$Sm, imm:$cc))*/]>,
987                  RegConstraint<"$Sn = $Sd">;
988 } // neverHasSideEffects
989
990 //===----------------------------------------------------------------------===//
991 // Move from VFP System Register to ARM core register.
992 //
993
994 class MovFromVFP<bits<4> opc19_16, dag oops, dag iops, string opc, string asm,
995                  list<dag> pattern>:
996   VFPAI<oops, iops, VFPMiscFrm, IIC_fpSTAT, opc, asm, pattern> {
997
998   // Instruction operand.
999   bits<4> Rt;
1000
1001   let Inst{27-20} = 0b11101111;
1002   let Inst{19-16} = opc19_16;
1003   let Inst{15-12} = Rt;
1004   let Inst{11-8}  = 0b1010;
1005   let Inst{7}     = 0;
1006   let Inst{6-5}   = 0b00;
1007   let Inst{4}     = 1;
1008   let Inst{3-0}   = 0b0000;
1009 }
1010
1011 // APSR is the application level alias of CPSR. This FPSCR N, Z, C, V flags
1012 // to APSR.
1013 let Defs = [CPSR], Uses = [FPSCR], Rt = 0b1111 /* apsr_nzcv */ in
1014 def FMSTAT : MovFromVFP<0b0001 /* fpscr */, (outs), (ins),
1015                         "vmrs", "\tapsr_nzcv, fpscr", [(arm_fmstat)]>;
1016
1017 // Application level FPSCR -> GPR
1018 let hasSideEffects = 1, Uses = [FPSCR] in
1019 def VMRS : MovFromVFP<0b0001 /* fpscr */, (outs GPR:$Rt), (ins),
1020                       "vmrs", "\t$Rt, fpscr",
1021                       [(set GPR:$Rt, (int_arm_get_fpscr))]>;
1022
1023 // System level FPEXC, FPSID -> GPR
1024 let Uses = [FPSCR] in {
1025   def VMRS_FPEXC : MovFromVFP<0b1000 /* fpexc */, (outs GPR:$Rt), (ins),
1026                               "vmrs", "\t$Rt, fpexc", []>;
1027   def VMRS_FPSID : MovFromVFP<0b0000 /* fpsid */, (outs GPR:$Rt), (ins),
1028                               "vmrs", "\t$Rt, fpsid", []>;
1029 }
1030
1031 //===----------------------------------------------------------------------===//
1032 // Move from ARM core register to VFP System Register.
1033 //
1034
1035 class MovToVFP<bits<4> opc19_16, dag oops, dag iops, string opc, string asm,
1036                list<dag> pattern>:
1037   VFPAI<oops, iops, VFPMiscFrm, IIC_fpSTAT, opc, asm, pattern> {
1038
1039   // Instruction operand.
1040   bits<4> src;
1041
1042   // Encode instruction operand.
1043   let Inst{15-12} = src;
1044
1045   let Inst{27-20} = 0b11101110;
1046   let Inst{19-16} = opc19_16;
1047   let Inst{11-8}  = 0b1010;
1048   let Inst{7}     = 0;
1049   let Inst{4}     = 1;
1050 }
1051
1052 let Defs = [FPSCR] in {
1053   // Application level GPR -> FPSCR
1054   def VMSR : MovToVFP<0b0001 /* fpscr */, (outs), (ins GPR:$src),
1055                       "vmsr", "\tfpscr, $src", [(int_arm_set_fpscr GPR:$src)]>;
1056   // System level GPR -> FPEXC
1057   def VMSR_FPEXC : MovToVFP<0b1000 /* fpexc */, (outs), (ins GPR:$src),
1058                       "vmsr", "\tfpexc, $src", []>;
1059   // System level GPR -> FPSID
1060   def VMSR_FPSID : MovToVFP<0b0000 /* fpsid */, (outs), (ins GPR:$src),
1061                       "vmsr", "\tfpsid, $src", []>;
1062 }
1063
1064 //===----------------------------------------------------------------------===//
1065 // Misc.
1066 //
1067
1068 // Materialize FP immediates. VFP3 only.
1069 let isReMaterializable = 1 in {
1070 def FCONSTD : VFPAI<(outs DPR:$Dd), (ins vfp_f64imm:$imm),
1071                     VFPMiscFrm, IIC_fpUNA64,
1072                     "vmov", ".f64\t$Dd, $imm",
1073                     [(set DPR:$Dd, vfp_f64imm:$imm)]>, Requires<[HasVFP3]> {
1074   // Instruction operands.
1075   bits<5>  Dd;
1076   bits<32> imm;
1077
1078   // Encode instruction operands.
1079   let Inst{15-12} = Dd{3-0};
1080   let Inst{22}    = Dd{4};
1081   let Inst{19}    = imm{31};
1082   let Inst{18-16} = imm{22-20};
1083   let Inst{3-0}   = imm{19-16};
1084
1085   // Encode remaining instruction bits.
1086   let Inst{27-23} = 0b11101;
1087   let Inst{21-20} = 0b11;
1088   let Inst{11-9}  = 0b101;
1089   let Inst{8}     = 1;          // Double precision.
1090   let Inst{7-4}   = 0b0000;
1091 }
1092
1093 def FCONSTS : VFPAI<(outs SPR:$Sd), (ins vfp_f32imm:$imm),
1094                      VFPMiscFrm, IIC_fpUNA32,
1095                      "vmov", ".f32\t$Sd, $imm",
1096                      [(set SPR:$Sd, vfp_f32imm:$imm)]>, Requires<[HasVFP3]> {
1097   // Instruction operands.
1098   bits<5>  Sd;
1099   bits<32> imm;
1100
1101   // Encode instruction operands.
1102   let Inst{15-12} = Sd{4-1};
1103   let Inst{22}    = Sd{0};
1104   let Inst{19}    = imm{31};    // The immediate is handled as a double.
1105   let Inst{18-16} = imm{22-20};
1106   let Inst{3-0}   = imm{19-16};
1107
1108   // Encode remaining instruction bits.
1109   let Inst{27-23} = 0b11101;
1110   let Inst{21-20} = 0b11;
1111   let Inst{11-9}  = 0b101;
1112   let Inst{8}     = 0;          // Single precision.
1113   let Inst{7-4}   = 0b0000;
1114 }
1115 }