add a missing type cast.
[oota-llvm.git] / lib / Target / X86 / X86InstrSSE.td
1 //====- X86InstrSSE.td - Describe the X86 Instruction Set --*- 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 X86 SSE instruction set, defining the instructions,
11 // and properties of the instructions which are needed for code generation,
12 // machine code emission, and analysis.
13 //
14 //===----------------------------------------------------------------------===//
15
16
17 //===----------------------------------------------------------------------===//
18 // SSE specific DAG Nodes.
19 //===----------------------------------------------------------------------===//
20
21 def SDTX86FPShiftOp : SDTypeProfile<1, 2, [ SDTCisSameAs<0, 1>,
22                                             SDTCisFP<0>, SDTCisInt<2> ]>;
23 def SDTX86VFCMP : SDTypeProfile<1, 3, [SDTCisInt<0>, SDTCisSameAs<1, 2>,
24                                        SDTCisFP<1>, SDTCisVT<3, i8>]>;
25
26 def X86fmin    : SDNode<"X86ISD::FMIN",      SDTFPBinOp>;
27 def X86fmax    : SDNode<"X86ISD::FMAX",      SDTFPBinOp>;
28 def X86fand    : SDNode<"X86ISD::FAND",      SDTFPBinOp,
29                         [SDNPCommutative, SDNPAssociative]>;
30 def X86for     : SDNode<"X86ISD::FOR",       SDTFPBinOp,
31                         [SDNPCommutative, SDNPAssociative]>;
32 def X86fxor    : SDNode<"X86ISD::FXOR",      SDTFPBinOp,
33                         [SDNPCommutative, SDNPAssociative]>;
34 def X86frsqrt  : SDNode<"X86ISD::FRSQRT",    SDTFPUnaryOp>;
35 def X86frcp    : SDNode<"X86ISD::FRCP",      SDTFPUnaryOp>;
36 def X86fsrl    : SDNode<"X86ISD::FSRL",      SDTX86FPShiftOp>;
37 def X86comi    : SDNode<"X86ISD::COMI",      SDTX86CmpTest>;
38 def X86ucomi   : SDNode<"X86ISD::UCOMI",     SDTX86CmpTest>;
39 def X86pshufb  : SDNode<"X86ISD::PSHUFB",
40                  SDTypeProfile<1, 2, [SDTCisVT<0, v16i8>, SDTCisSameAs<0,1>,
41                                       SDTCisSameAs<0,2>]>>;
42 def X86pextrb  : SDNode<"X86ISD::PEXTRB",
43                  SDTypeProfile<1, 2, [SDTCisVT<0, i32>, SDTCisPtrTy<2>]>>;
44 def X86pextrw  : SDNode<"X86ISD::PEXTRW",
45                  SDTypeProfile<1, 2, [SDTCisVT<0, i32>, SDTCisPtrTy<2>]>>;
46 def X86pinsrb  : SDNode<"X86ISD::PINSRB",
47                  SDTypeProfile<1, 3, [SDTCisVT<0, v16i8>, SDTCisSameAs<0,1>,
48                                       SDTCisVT<2, i32>, SDTCisPtrTy<3>]>>;
49 def X86pinsrw  : SDNode<"X86ISD::PINSRW",
50                  SDTypeProfile<1, 3, [SDTCisVT<0, v8i16>, SDTCisSameAs<0,1>,
51                                       SDTCisVT<2, i32>, SDTCisPtrTy<3>]>>;
52 def X86insrtps : SDNode<"X86ISD::INSERTPS",
53                  SDTypeProfile<1, 3, [SDTCisVT<0, v4f32>, SDTCisSameAs<0,1>,
54                                       SDTCisVT<2, v4f32>, SDTCisPtrTy<3>]>>;
55 def X86vzmovl  : SDNode<"X86ISD::VZEXT_MOVL",
56                  SDTypeProfile<1, 1, [SDTCisSameAs<0,1>]>>;
57 def X86vzload  : SDNode<"X86ISD::VZEXT_LOAD", SDTLoad,
58                         [SDNPHasChain, SDNPMayLoad]>;
59 def X86vshl    : SDNode<"X86ISD::VSHL",      SDTIntShiftOp>;
60 def X86vshr    : SDNode<"X86ISD::VSRL",      SDTIntShiftOp>;
61 def X86cmpps   : SDNode<"X86ISD::CMPPS",     SDTX86VFCMP>;
62 def X86cmppd   : SDNode<"X86ISD::CMPPD",     SDTX86VFCMP>;
63 def X86pcmpeqb : SDNode<"X86ISD::PCMPEQB", SDTIntBinOp, [SDNPCommutative]>;
64 def X86pcmpeqw : SDNode<"X86ISD::PCMPEQW", SDTIntBinOp, [SDNPCommutative]>;
65 def X86pcmpeqd : SDNode<"X86ISD::PCMPEQD", SDTIntBinOp, [SDNPCommutative]>;
66 def X86pcmpeqq : SDNode<"X86ISD::PCMPEQQ", SDTIntBinOp, [SDNPCommutative]>;
67 def X86pcmpgtb : SDNode<"X86ISD::PCMPGTB", SDTIntBinOp>;
68 def X86pcmpgtw : SDNode<"X86ISD::PCMPGTW", SDTIntBinOp>;
69 def X86pcmpgtd : SDNode<"X86ISD::PCMPGTD", SDTIntBinOp>;
70 def X86pcmpgtq : SDNode<"X86ISD::PCMPGTQ", SDTIntBinOp>;
71
72 def SDTX86CmpPTest : SDTypeProfile<0, 2, [SDTCisVT<0, v4f32>,
73                                           SDTCisVT<1, v4f32>]>;
74 def X86ptest   : SDNode<"X86ISD::PTEST", SDTX86CmpPTest>;
75
76 //===----------------------------------------------------------------------===//
77 // SSE Complex Patterns
78 //===----------------------------------------------------------------------===//
79
80 // These are 'extloads' from a scalar to the low element of a vector, zeroing
81 // the top elements.  These are used for the SSE 'ss' and 'sd' instruction
82 // forms.
83 def sse_load_f32 : ComplexPattern<v4f32, 5, "SelectScalarSSELoad", [],
84                                   [SDNPHasChain, SDNPMayLoad]>;
85 def sse_load_f64 : ComplexPattern<v2f64, 5, "SelectScalarSSELoad", [],
86                                   [SDNPHasChain, SDNPMayLoad]>;
87
88 def ssmem : Operand<v4f32> {
89   let PrintMethod = "printf32mem";
90   let MIOperandInfo = (ops ptr_rc, i8imm, ptr_rc_nosp, i32imm, i8imm);
91   let ParserMatchClass = X86MemAsmOperand;
92 }
93 def sdmem : Operand<v2f64> {
94   let PrintMethod = "printf64mem";
95   let MIOperandInfo = (ops ptr_rc, i8imm, ptr_rc_nosp, i32imm, i8imm);
96   let ParserMatchClass = X86MemAsmOperand;
97 }
98
99 //===----------------------------------------------------------------------===//
100 // SSE pattern fragments
101 //===----------------------------------------------------------------------===//
102
103 def loadv4f32    : PatFrag<(ops node:$ptr), (v4f32 (load node:$ptr))>;
104 def loadv2f64    : PatFrag<(ops node:$ptr), (v2f64 (load node:$ptr))>;
105 def loadv4i32    : PatFrag<(ops node:$ptr), (v4i32 (load node:$ptr))>;
106 def loadv2i64    : PatFrag<(ops node:$ptr), (v2i64 (load node:$ptr))>;
107
108 // Like 'store', but always requires vector alignment.
109 def alignedstore : PatFrag<(ops node:$val, node:$ptr),
110                            (store node:$val, node:$ptr), [{
111   return cast<StoreSDNode>(N)->getAlignment() >= 16;
112 }]>;
113
114 // Like 'load', but always requires vector alignment.
115 def alignedload : PatFrag<(ops node:$ptr), (load node:$ptr), [{
116   return cast<LoadSDNode>(N)->getAlignment() >= 16;
117 }]>;
118
119 def alignedloadfsf32 : PatFrag<(ops node:$ptr), 
120                                (f32 (alignedload node:$ptr))>;
121 def alignedloadfsf64 : PatFrag<(ops node:$ptr), 
122                                (f64 (alignedload node:$ptr))>;
123 def alignedloadv4f32 : PatFrag<(ops node:$ptr), 
124                                (v4f32 (alignedload node:$ptr))>;
125 def alignedloadv2f64 : PatFrag<(ops node:$ptr), 
126                                (v2f64 (alignedload node:$ptr))>;
127 def alignedloadv4i32 : PatFrag<(ops node:$ptr), 
128                                (v4i32 (alignedload node:$ptr))>;
129 def alignedloadv2i64 : PatFrag<(ops node:$ptr), 
130                                (v2i64 (alignedload node:$ptr))>;
131
132 // Like 'load', but uses special alignment checks suitable for use in
133 // memory operands in most SSE instructions, which are required to
134 // be naturally aligned on some targets but not on others.  If the subtarget
135 // allows unaligned accesses, match any load, though this may require
136 // setting a feature bit in the processor (on startup, for example).
137 // Opteron 10h and later implement such a feature.
138 def memop : PatFrag<(ops node:$ptr), (load node:$ptr), [{
139   return    Subtarget->hasVectorUAMem()
140          || cast<LoadSDNode>(N)->getAlignment() >= 16;
141 }]>;
142
143 def memopfsf32 : PatFrag<(ops node:$ptr), (f32   (memop node:$ptr))>;
144 def memopfsf64 : PatFrag<(ops node:$ptr), (f64   (memop node:$ptr))>;
145 def memopv4f32 : PatFrag<(ops node:$ptr), (v4f32 (memop node:$ptr))>;
146 def memopv2f64 : PatFrag<(ops node:$ptr), (v2f64 (memop node:$ptr))>;
147 def memopv4i32 : PatFrag<(ops node:$ptr), (v4i32 (memop node:$ptr))>;
148 def memopv2i64 : PatFrag<(ops node:$ptr), (v2i64 (memop node:$ptr))>;
149 def memopv16i8 : PatFrag<(ops node:$ptr), (v16i8 (memop node:$ptr))>;
150
151 // SSSE3 uses MMX registers for some instructions. They aren't aligned on a
152 // 16-byte boundary.
153 // FIXME: 8 byte alignment for mmx reads is not required
154 def memop64 : PatFrag<(ops node:$ptr), (load node:$ptr), [{
155   return cast<LoadSDNode>(N)->getAlignment() >= 8;
156 }]>;
157
158 def memopv8i8  : PatFrag<(ops node:$ptr), (v8i8  (memop64 node:$ptr))>;
159 def memopv4i16 : PatFrag<(ops node:$ptr), (v4i16 (memop64 node:$ptr))>;
160 def memopv8i16 : PatFrag<(ops node:$ptr), (v8i16 (memop64 node:$ptr))>;
161 def memopv2i32 : PatFrag<(ops node:$ptr), (v2i32 (memop64 node:$ptr))>;
162
163 // MOVNT Support
164 // Like 'store', but requires the non-temporal bit to be set
165 def nontemporalstore : PatFrag<(ops node:$val, node:$ptr),
166                            (st node:$val, node:$ptr), [{
167   if (StoreSDNode *ST = dyn_cast<StoreSDNode>(N))
168     return ST->isNonTemporal();
169   return false;
170 }]>;
171
172 def alignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
173                                    (st node:$val, node:$ptr), [{
174   if (StoreSDNode *ST = dyn_cast<StoreSDNode>(N))
175     return ST->isNonTemporal() && !ST->isTruncatingStore() &&
176            ST->getAddressingMode() == ISD::UNINDEXED &&
177            ST->getAlignment() >= 16;
178   return false;
179 }]>;
180
181 def unalignednontemporalstore : PatFrag<(ops node:$val, node:$ptr),
182                                    (st node:$val, node:$ptr), [{
183   if (StoreSDNode *ST = dyn_cast<StoreSDNode>(N))
184     return ST->isNonTemporal() &&
185            ST->getAlignment() < 16;
186   return false;
187 }]>;
188
189 def bc_v4f32 : PatFrag<(ops node:$in), (v4f32 (bitconvert node:$in))>;
190 def bc_v2f64 : PatFrag<(ops node:$in), (v2f64 (bitconvert node:$in))>;
191 def bc_v16i8 : PatFrag<(ops node:$in), (v16i8 (bitconvert node:$in))>;
192 def bc_v8i16 : PatFrag<(ops node:$in), (v8i16 (bitconvert node:$in))>;
193 def bc_v4i32 : PatFrag<(ops node:$in), (v4i32 (bitconvert node:$in))>;
194 def bc_v2i64 : PatFrag<(ops node:$in), (v2i64 (bitconvert node:$in))>;
195
196 def vzmovl_v2i64 : PatFrag<(ops node:$src),
197                            (bitconvert (v2i64 (X86vzmovl
198                              (v2i64 (scalar_to_vector (loadi64 node:$src))))))>;
199 def vzmovl_v4i32 : PatFrag<(ops node:$src),
200                            (bitconvert (v4i32 (X86vzmovl
201                              (v4i32 (scalar_to_vector (loadi32 node:$src))))))>;
202
203 def vzload_v2i64 : PatFrag<(ops node:$src),
204                            (bitconvert (v2i64 (X86vzload node:$src)))>;
205
206
207 def fp32imm0 : PatLeaf<(f32 fpimm), [{
208   return N->isExactlyValue(+0.0);
209 }]>;
210
211 // BYTE_imm - Transform bit immediates into byte immediates.
212 def BYTE_imm  : SDNodeXForm<imm, [{
213   // Transformation function: imm >> 3
214   return getI32Imm(N->getZExtValue() >> 3);
215 }]>;
216
217 // SHUFFLE_get_shuf_imm xform function: convert vector_shuffle mask to PSHUF*,
218 // SHUFP* etc. imm.
219 def SHUFFLE_get_shuf_imm : SDNodeXForm<vector_shuffle, [{
220   return getI8Imm(X86::getShuffleSHUFImmediate(N));
221 }]>;
222
223 // SHUFFLE_get_pshufhw_imm xform function: convert vector_shuffle mask to
224 // PSHUFHW imm.
225 def SHUFFLE_get_pshufhw_imm : SDNodeXForm<vector_shuffle, [{
226   return getI8Imm(X86::getShufflePSHUFHWImmediate(N));
227 }]>;
228
229 // SHUFFLE_get_pshuflw_imm xform function: convert vector_shuffle mask to
230 // PSHUFLW imm.
231 def SHUFFLE_get_pshuflw_imm : SDNodeXForm<vector_shuffle, [{
232   return getI8Imm(X86::getShufflePSHUFLWImmediate(N));
233 }]>;
234
235 // SHUFFLE_get_palign_imm xform function: convert vector_shuffle mask to
236 // a PALIGNR imm.
237 def SHUFFLE_get_palign_imm : SDNodeXForm<vector_shuffle, [{
238   return getI8Imm(X86::getShufflePALIGNRImmediate(N));
239 }]>;
240
241 def splat_lo : PatFrag<(ops node:$lhs, node:$rhs),
242                        (vector_shuffle node:$lhs, node:$rhs), [{
243   ShuffleVectorSDNode *SVOp = cast<ShuffleVectorSDNode>(N);
244   return SVOp->isSplat() && SVOp->getSplatIndex() == 0;
245 }]>;
246
247 def movddup : PatFrag<(ops node:$lhs, node:$rhs),
248                       (vector_shuffle node:$lhs, node:$rhs), [{
249   return X86::isMOVDDUPMask(cast<ShuffleVectorSDNode>(N));
250 }]>;
251
252 def movhlps : PatFrag<(ops node:$lhs, node:$rhs),
253                       (vector_shuffle node:$lhs, node:$rhs), [{
254   return X86::isMOVHLPSMask(cast<ShuffleVectorSDNode>(N));
255 }]>;
256
257 def movhlps_undef : PatFrag<(ops node:$lhs, node:$rhs),
258                             (vector_shuffle node:$lhs, node:$rhs), [{
259   return X86::isMOVHLPS_v_undef_Mask(cast<ShuffleVectorSDNode>(N));
260 }]>;
261
262 def movlhps : PatFrag<(ops node:$lhs, node:$rhs),
263                       (vector_shuffle node:$lhs, node:$rhs), [{
264   return X86::isMOVLHPSMask(cast<ShuffleVectorSDNode>(N));
265 }]>;
266
267 def movlp : PatFrag<(ops node:$lhs, node:$rhs),
268                     (vector_shuffle node:$lhs, node:$rhs), [{
269   return X86::isMOVLPMask(cast<ShuffleVectorSDNode>(N));
270 }]>;
271
272 def movl : PatFrag<(ops node:$lhs, node:$rhs),
273                    (vector_shuffle node:$lhs, node:$rhs), [{
274   return X86::isMOVLMask(cast<ShuffleVectorSDNode>(N));
275 }]>;
276
277 def movshdup : PatFrag<(ops node:$lhs, node:$rhs),
278                        (vector_shuffle node:$lhs, node:$rhs), [{
279   return X86::isMOVSHDUPMask(cast<ShuffleVectorSDNode>(N));
280 }]>;
281
282 def movsldup : PatFrag<(ops node:$lhs, node:$rhs),
283                        (vector_shuffle node:$lhs, node:$rhs), [{
284   return X86::isMOVSLDUPMask(cast<ShuffleVectorSDNode>(N));
285 }]>;
286
287 def unpckl : PatFrag<(ops node:$lhs, node:$rhs),
288                      (vector_shuffle node:$lhs, node:$rhs), [{
289   return X86::isUNPCKLMask(cast<ShuffleVectorSDNode>(N));
290 }]>;
291
292 def unpckh : PatFrag<(ops node:$lhs, node:$rhs),
293                      (vector_shuffle node:$lhs, node:$rhs), [{
294   return X86::isUNPCKHMask(cast<ShuffleVectorSDNode>(N));
295 }]>;
296
297 def unpckl_undef : PatFrag<(ops node:$lhs, node:$rhs),
298                            (vector_shuffle node:$lhs, node:$rhs), [{
299   return X86::isUNPCKL_v_undef_Mask(cast<ShuffleVectorSDNode>(N));
300 }]>;
301
302 def unpckh_undef : PatFrag<(ops node:$lhs, node:$rhs),
303                            (vector_shuffle node:$lhs, node:$rhs), [{
304   return X86::isUNPCKH_v_undef_Mask(cast<ShuffleVectorSDNode>(N));
305 }]>;
306
307 def pshufd : PatFrag<(ops node:$lhs, node:$rhs),
308                      (vector_shuffle node:$lhs, node:$rhs), [{
309   return X86::isPSHUFDMask(cast<ShuffleVectorSDNode>(N));
310 }], SHUFFLE_get_shuf_imm>;
311
312 def shufp : PatFrag<(ops node:$lhs, node:$rhs),
313                     (vector_shuffle node:$lhs, node:$rhs), [{
314   return X86::isSHUFPMask(cast<ShuffleVectorSDNode>(N));
315 }], SHUFFLE_get_shuf_imm>;
316
317 def pshufhw : PatFrag<(ops node:$lhs, node:$rhs),
318                       (vector_shuffle node:$lhs, node:$rhs), [{
319   return X86::isPSHUFHWMask(cast<ShuffleVectorSDNode>(N));
320 }], SHUFFLE_get_pshufhw_imm>;
321
322 def pshuflw : PatFrag<(ops node:$lhs, node:$rhs),
323                       (vector_shuffle node:$lhs, node:$rhs), [{
324   return X86::isPSHUFLWMask(cast<ShuffleVectorSDNode>(N));
325 }], SHUFFLE_get_pshuflw_imm>;
326
327 def palign : PatFrag<(ops node:$lhs, node:$rhs),
328                      (vector_shuffle node:$lhs, node:$rhs), [{
329   return X86::isPALIGNRMask(cast<ShuffleVectorSDNode>(N));
330 }], SHUFFLE_get_palign_imm>;
331
332 //===----------------------------------------------------------------------===//
333 // SSE scalar FP Instructions
334 //===----------------------------------------------------------------------===//
335
336 // CMOV* - Used to implement the SSE SELECT DAG operation.  Expanded after
337 // instruction selection into a branch sequence.
338 let Uses = [EFLAGS], usesCustomInserter = 1 in {
339   def CMOV_FR32 : I<0, Pseudo,
340                     (outs FR32:$dst), (ins FR32:$t, FR32:$f, i8imm:$cond),
341                     "#CMOV_FR32 PSEUDO!",
342                     [(set FR32:$dst, (X86cmov FR32:$t, FR32:$f, imm:$cond,
343                                                   EFLAGS))]>;
344   def CMOV_FR64 : I<0, Pseudo,
345                     (outs FR64:$dst), (ins FR64:$t, FR64:$f, i8imm:$cond),
346                     "#CMOV_FR64 PSEUDO!",
347                     [(set FR64:$dst, (X86cmov FR64:$t, FR64:$f, imm:$cond,
348                                                   EFLAGS))]>;
349   def CMOV_V4F32 : I<0, Pseudo,
350                     (outs VR128:$dst), (ins VR128:$t, VR128:$f, i8imm:$cond),
351                     "#CMOV_V4F32 PSEUDO!",
352                     [(set VR128:$dst,
353                       (v4f32 (X86cmov VR128:$t, VR128:$f, imm:$cond,
354                                           EFLAGS)))]>;
355   def CMOV_V2F64 : I<0, Pseudo,
356                     (outs VR128:$dst), (ins VR128:$t, VR128:$f, i8imm:$cond),
357                     "#CMOV_V2F64 PSEUDO!",
358                     [(set VR128:$dst,
359                       (v2f64 (X86cmov VR128:$t, VR128:$f, imm:$cond,
360                                           EFLAGS)))]>;
361   def CMOV_V2I64 : I<0, Pseudo,
362                     (outs VR128:$dst), (ins VR128:$t, VR128:$f, i8imm:$cond),
363                     "#CMOV_V2I64 PSEUDO!",
364                     [(set VR128:$dst,
365                       (v2i64 (X86cmov VR128:$t, VR128:$f, imm:$cond,
366                                           EFLAGS)))]>;
367 }
368
369 //===----------------------------------------------------------------------===//
370 // SSE1 Instructions
371 //===----------------------------------------------------------------------===//
372
373 // Move Instructions
374 let neverHasSideEffects = 1 in
375 def MOVSSrr : SSI<0x10, MRMSrcReg, (outs FR32:$dst), (ins FR32:$src),
376                   "movss\t{$src, $dst|$dst, $src}", []>;
377 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
378 def MOVSSrm : SSI<0x10, MRMSrcMem, (outs FR32:$dst), (ins f32mem:$src),
379                   "movss\t{$src, $dst|$dst, $src}",
380                   [(set FR32:$dst, (loadf32 addr:$src))]>;
381 def MOVSSmr : SSI<0x11, MRMDestMem, (outs), (ins f32mem:$dst, FR32:$src),
382                   "movss\t{$src, $dst|$dst, $src}",
383                   [(store FR32:$src, addr:$dst)]>;
384
385 // Conversion instructions
386 def CVTTSS2SIrr : SSI<0x2C, MRMSrcReg, (outs GR32:$dst), (ins FR32:$src),
387                       "cvttss2si\t{$src, $dst|$dst, $src}",
388                       [(set GR32:$dst, (fp_to_sint FR32:$src))]>;
389 def CVTTSS2SIrm : SSI<0x2C, MRMSrcMem, (outs GR32:$dst), (ins f32mem:$src),
390                       "cvttss2si\t{$src, $dst|$dst, $src}",
391                       [(set GR32:$dst, (fp_to_sint (loadf32 addr:$src)))]>;
392 def CVTSI2SSrr  : SSI<0x2A, MRMSrcReg, (outs FR32:$dst), (ins GR32:$src),
393                       "cvtsi2ss\t{$src, $dst|$dst, $src}",
394                       [(set FR32:$dst, (sint_to_fp GR32:$src))]>;
395 def CVTSI2SSrm  : SSI<0x2A, MRMSrcMem, (outs FR32:$dst), (ins i32mem:$src),
396                       "cvtsi2ss\t{$src, $dst|$dst, $src}",
397                       [(set FR32:$dst, (sint_to_fp (loadi32 addr:$src)))]>;
398
399 // Match intrinsics which expect XMM operand(s).
400 def CVTSS2SIrr: SSI<0x2D, MRMSrcReg, (outs GR32:$dst), (ins FR32:$src),
401                     "cvtss2si{l}\t{$src, $dst|$dst, $src}", []>;
402 def CVTSS2SIrm: SSI<0x2D, MRMSrcMem, (outs GR32:$dst), (ins f32mem:$src),
403                     "cvtss2si{l}\t{$src, $dst|$dst, $src}", []>;
404
405 def Int_CVTSS2SIrr : SSI<0x2D, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
406                          "cvtss2si\t{$src, $dst|$dst, $src}",
407                          [(set GR32:$dst, (int_x86_sse_cvtss2si VR128:$src))]>;
408 def Int_CVTSS2SIrm : SSI<0x2D, MRMSrcMem, (outs GR32:$dst), (ins f32mem:$src),
409                          "cvtss2si\t{$src, $dst|$dst, $src}",
410                          [(set GR32:$dst, (int_x86_sse_cvtss2si
411                                            (load addr:$src)))]>;
412
413 // Match intrinisics which expect MM and XMM operand(s).
414 def Int_CVTPS2PIrr : PSI<0x2D, MRMSrcReg, (outs VR64:$dst), (ins VR128:$src),
415                          "cvtps2pi\t{$src, $dst|$dst, $src}",
416                          [(set VR64:$dst, (int_x86_sse_cvtps2pi VR128:$src))]>;
417 def Int_CVTPS2PIrm : PSI<0x2D, MRMSrcMem, (outs VR64:$dst), (ins f64mem:$src),
418                          "cvtps2pi\t{$src, $dst|$dst, $src}",
419                          [(set VR64:$dst, (int_x86_sse_cvtps2pi
420                                            (load addr:$src)))]>;
421 def Int_CVTTPS2PIrr: PSI<0x2C, MRMSrcReg, (outs VR64:$dst), (ins VR128:$src),
422                          "cvttps2pi\t{$src, $dst|$dst, $src}",
423                          [(set VR64:$dst, (int_x86_sse_cvttps2pi VR128:$src))]>;
424 def Int_CVTTPS2PIrm: PSI<0x2C, MRMSrcMem, (outs VR64:$dst), (ins f64mem:$src),
425                          "cvttps2pi\t{$src, $dst|$dst, $src}",
426                          [(set VR64:$dst, (int_x86_sse_cvttps2pi
427                                            (load addr:$src)))]>;
428 let Constraints = "$src1 = $dst" in {
429   def Int_CVTPI2PSrr : PSI<0x2A, MRMSrcReg,
430                            (outs VR128:$dst), (ins VR128:$src1, VR64:$src2),
431                         "cvtpi2ps\t{$src2, $dst|$dst, $src2}",
432                         [(set VR128:$dst, (int_x86_sse_cvtpi2ps VR128:$src1,
433                                            VR64:$src2))]>;
434   def Int_CVTPI2PSrm : PSI<0x2A, MRMSrcMem,
435                            (outs VR128:$dst), (ins VR128:$src1, i64mem:$src2),
436                         "cvtpi2ps\t{$src2, $dst|$dst, $src2}",
437                         [(set VR128:$dst, (int_x86_sse_cvtpi2ps VR128:$src1,
438                                             (load addr:$src2)))]>;
439 }
440
441 // Aliases for intrinsics
442 def Int_CVTTSS2SIrr : SSI<0x2C, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
443                           "cvttss2si\t{$src, $dst|$dst, $src}",
444                           [(set GR32:$dst,
445                             (int_x86_sse_cvttss2si VR128:$src))]>;
446 def Int_CVTTSS2SIrm : SSI<0x2C, MRMSrcMem, (outs GR32:$dst), (ins f32mem:$src),
447                           "cvttss2si\t{$src, $dst|$dst, $src}",
448                           [(set GR32:$dst,
449                             (int_x86_sse_cvttss2si(load addr:$src)))]>;
450
451 let Constraints = "$src1 = $dst" in {
452   def Int_CVTSI2SSrr : SSI<0x2A, MRMSrcReg,
453                            (outs VR128:$dst), (ins VR128:$src1, GR32:$src2),
454                            "cvtsi2ss\t{$src2, $dst|$dst, $src2}",
455                            [(set VR128:$dst, (int_x86_sse_cvtsi2ss VR128:$src1,
456                                               GR32:$src2))]>;
457   def Int_CVTSI2SSrm : SSI<0x2A, MRMSrcMem,
458                            (outs VR128:$dst), (ins VR128:$src1, i32mem:$src2),
459                            "cvtsi2ss\t{$src2, $dst|$dst, $src2}",
460                            [(set VR128:$dst, (int_x86_sse_cvtsi2ss VR128:$src1,
461                                               (loadi32 addr:$src2)))]>;
462 }
463
464 // Comparison instructions
465 let Constraints = "$src1 = $dst", neverHasSideEffects = 1 in {
466   def CMPSSrr : SSIi8<0xC2, MRMSrcReg,
467                     (outs FR32:$dst), (ins FR32:$src1, FR32:$src, SSECC:$cc),
468                     "cmp${cc}ss\t{$src, $dst|$dst, $src}", []>;
469 let mayLoad = 1 in
470   def CMPSSrm : SSIi8<0xC2, MRMSrcMem,
471                     (outs FR32:$dst), (ins FR32:$src1, f32mem:$src, SSECC:$cc),
472                     "cmp${cc}ss\t{$src, $dst|$dst, $src}", []>;
473 }
474
475 let Defs = [EFLAGS] in {
476 def UCOMISSrr: PSI<0x2E, MRMSrcReg, (outs), (ins FR32:$src1, FR32:$src2),
477                    "ucomiss\t{$src2, $src1|$src1, $src2}",
478                    [(X86cmp FR32:$src1, FR32:$src2), (implicit EFLAGS)]>;
479 def UCOMISSrm: PSI<0x2E, MRMSrcMem, (outs), (ins FR32:$src1, f32mem:$src2),
480                    "ucomiss\t{$src2, $src1|$src1, $src2}",
481                    [(X86cmp FR32:$src1, (loadf32 addr:$src2)),
482                     (implicit EFLAGS)]>;
483                     
484 def COMISSrr: PSI<0x2F, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
485                   "comiss\t{$src2, $src1|$src1, $src2}", []>;
486 def COMISSrm: PSI<0x2F, MRMSrcMem, (outs), (ins VR128:$src1, f128mem:$src2),
487                   "comiss\t{$src2, $src1|$src1, $src2}", []>;
488                   
489 } // Defs = [EFLAGS]
490
491 // Aliases to match intrinsics which expect XMM operand(s).
492 let Constraints = "$src1 = $dst" in {
493   def Int_CMPSSrr : SSIi8<0xC2, MRMSrcReg,
494                         (outs VR128:$dst), 
495                         (ins VR128:$src1, VR128:$src, SSECC:$cc),
496                         "cmp${cc}ss\t{$src, $dst|$dst, $src}",
497                         [(set VR128:$dst, (int_x86_sse_cmp_ss 
498                                              VR128:$src1,
499                                              VR128:$src, imm:$cc))]>;
500   def Int_CMPSSrm : SSIi8<0xC2, MRMSrcMem,
501                         (outs VR128:$dst), 
502                         (ins VR128:$src1, f32mem:$src, SSECC:$cc),
503                         "cmp${cc}ss\t{$src, $dst|$dst, $src}",
504                         [(set VR128:$dst, (int_x86_sse_cmp_ss VR128:$src1,
505                                            (load addr:$src), imm:$cc))]>;
506 }
507
508 let Defs = [EFLAGS] in {
509 def Int_UCOMISSrr: PSI<0x2E, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
510                        "ucomiss\t{$src2, $src1|$src1, $src2}",
511                        [(X86ucomi (v4f32 VR128:$src1), VR128:$src2),
512                         (implicit EFLAGS)]>;
513 def Int_UCOMISSrm: PSI<0x2E, MRMSrcMem, (outs),(ins VR128:$src1, f128mem:$src2),
514                        "ucomiss\t{$src2, $src1|$src1, $src2}",
515                        [(X86ucomi (v4f32 VR128:$src1), (load addr:$src2)),
516                         (implicit EFLAGS)]>;
517
518 def Int_COMISSrr: PSI<0x2F, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
519                       "comiss\t{$src2, $src1|$src1, $src2}",
520                       [(X86comi (v4f32 VR128:$src1), VR128:$src2),
521                        (implicit EFLAGS)]>;
522 def Int_COMISSrm: PSI<0x2F, MRMSrcMem, (outs), (ins VR128:$src1, f128mem:$src2),
523                       "comiss\t{$src2, $src1|$src1, $src2}",
524                       [(X86comi (v4f32 VR128:$src1), (load addr:$src2)),
525                        (implicit EFLAGS)]>;
526 } // Defs = [EFLAGS]
527
528 // Aliases of packed SSE1 instructions for scalar use. These all have names
529 // that start with 'Fs'.
530
531 // Alias instructions that map fld0 to pxor for sse.
532 let isReMaterializable = 1, isAsCheapAsAMove = 1, isCodeGenOnly = 1,
533     canFoldAsLoad = 1 in
534   // FIXME: Set encoding to pseudo!
535 def FsFLD0SS : I<0xEF, MRMInitReg, (outs FR32:$dst), (ins), "",
536                  [(set FR32:$dst, fp32imm0)]>,
537                  Requires<[HasSSE1]>, TB, OpSize;
538
539 // Alias instruction to do FR32 reg-to-reg copy using movaps. Upper bits are
540 // disregarded.
541 let neverHasSideEffects = 1 in
542 def FsMOVAPSrr : PSI<0x28, MRMSrcReg, (outs FR32:$dst), (ins FR32:$src),
543                      "movaps\t{$src, $dst|$dst, $src}", []>;
544
545 // Alias instruction to load FR32 from f128mem using movaps. Upper bits are
546 // disregarded.
547 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
548 def FsMOVAPSrm : PSI<0x28, MRMSrcMem, (outs FR32:$dst), (ins f128mem:$src),
549                      "movaps\t{$src, $dst|$dst, $src}",
550                      [(set FR32:$dst, (alignedloadfsf32 addr:$src))]>;
551
552 // Alias bitwise logical operations using SSE logical ops on packed FP values.
553 let Constraints = "$src1 = $dst" in {
554 let isCommutable = 1 in {
555   def FsANDPSrr : PSI<0x54, MRMSrcReg, (outs FR32:$dst),
556                                        (ins FR32:$src1, FR32:$src2),
557                       "andps\t{$src2, $dst|$dst, $src2}",
558                       [(set FR32:$dst, (X86fand FR32:$src1, FR32:$src2))]>;
559   def FsORPSrr  : PSI<0x56, MRMSrcReg, (outs FR32:$dst),
560                                        (ins FR32:$src1, FR32:$src2),
561                       "orps\t{$src2, $dst|$dst, $src2}",
562                       [(set FR32:$dst, (X86for FR32:$src1, FR32:$src2))]>;
563   def FsXORPSrr : PSI<0x57, MRMSrcReg, (outs FR32:$dst),
564                                        (ins FR32:$src1, FR32:$src2),
565                       "xorps\t{$src2, $dst|$dst, $src2}",
566                       [(set FR32:$dst, (X86fxor FR32:$src1, FR32:$src2))]>;
567 }
568
569 def FsANDPSrm : PSI<0x54, MRMSrcMem, (outs FR32:$dst),
570                                      (ins FR32:$src1, f128mem:$src2),
571                     "andps\t{$src2, $dst|$dst, $src2}",
572                     [(set FR32:$dst, (X86fand FR32:$src1,
573                                       (memopfsf32 addr:$src2)))]>;
574 def FsORPSrm  : PSI<0x56, MRMSrcMem, (outs FR32:$dst),
575                                      (ins FR32:$src1, f128mem:$src2),
576                     "orps\t{$src2, $dst|$dst, $src2}",
577                     [(set FR32:$dst, (X86for FR32:$src1,
578                                       (memopfsf32 addr:$src2)))]>;
579 def FsXORPSrm : PSI<0x57, MRMSrcMem, (outs FR32:$dst),
580                                      (ins FR32:$src1, f128mem:$src2),
581                     "xorps\t{$src2, $dst|$dst, $src2}",
582                     [(set FR32:$dst, (X86fxor FR32:$src1,
583                                       (memopfsf32 addr:$src2)))]>;
584
585 let neverHasSideEffects = 1 in {
586 def FsANDNPSrr : PSI<0x55, MRMSrcReg,
587                      (outs FR32:$dst), (ins FR32:$src1, FR32:$src2),
588                      "andnps\t{$src2, $dst|$dst, $src2}", []>;
589 let mayLoad = 1 in
590 def FsANDNPSrm : PSI<0x55, MRMSrcMem,
591                      (outs FR32:$dst), (ins FR32:$src1, f128mem:$src2),
592                      "andnps\t{$src2, $dst|$dst, $src2}", []>;
593 }
594 }
595
596 /// basic_sse1_fp_binop_rm - SSE1 binops come in both scalar and vector forms.
597 ///
598 /// In addition, we also have a special variant of the scalar form here to
599 /// represent the associated intrinsic operation.  This form is unlike the
600 /// plain scalar form, in that it takes an entire vector (instead of a scalar)
601 /// and leaves the top elements unmodified (therefore these cannot be commuted).
602 ///
603 /// These three forms can each be reg+reg or reg+mem, so there are a total of
604 /// six "instructions".
605 ///
606 let Constraints = "$src1 = $dst" in {
607 multiclass basic_sse1_fp_binop_rm<bits<8> opc, string OpcodeStr,
608                                   SDNode OpNode, Intrinsic F32Int,
609                                   bit Commutable = 0> {
610   // Scalar operation, reg+reg.
611   def SSrr : SSI<opc, MRMSrcReg, (outs FR32:$dst), (ins FR32:$src1, FR32:$src2),
612                  !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
613                  [(set FR32:$dst, (OpNode FR32:$src1, FR32:$src2))]> {
614     let isCommutable = Commutable;
615   }
616
617   // Scalar operation, reg+mem.
618   def SSrm : SSI<opc, MRMSrcMem, (outs FR32:$dst),
619                                  (ins FR32:$src1, f32mem:$src2),
620                  !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
621                  [(set FR32:$dst, (OpNode FR32:$src1, (load addr:$src2)))]>;
622
623   // Vector operation, reg+reg.
624   def PSrr : PSI<opc, MRMSrcReg, (outs VR128:$dst),
625                                  (ins VR128:$src1, VR128:$src2),
626                !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
627                [(set VR128:$dst, (v4f32 (OpNode VR128:$src1, VR128:$src2)))]> {
628     let isCommutable = Commutable;
629   }
630
631   // Vector operation, reg+mem.
632   def PSrm : PSI<opc, MRMSrcMem, (outs VR128:$dst),
633                                  (ins VR128:$src1, f128mem:$src2),
634                  !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
635              [(set VR128:$dst, (OpNode VR128:$src1, (memopv4f32 addr:$src2)))]>;
636
637   // Intrinsic operation, reg+reg.
638   def SSrr_Int : SSI<opc, MRMSrcReg, (outs VR128:$dst),
639                                      (ins VR128:$src1, VR128:$src2),
640                      !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
641                      [(set VR128:$dst, (F32Int VR128:$src1, VR128:$src2))]>;
642
643   // Intrinsic operation, reg+mem.
644   def SSrm_Int : SSI<opc, MRMSrcMem, (outs VR128:$dst),
645                                      (ins VR128:$src1, ssmem:$src2),
646                      !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
647                      [(set VR128:$dst, (F32Int VR128:$src1,
648                                                sse_load_f32:$src2))]>;
649 }
650 }
651
652 // Arithmetic instructions
653 defm ADD : basic_sse1_fp_binop_rm<0x58, "add", fadd, int_x86_sse_add_ss, 1>;
654 defm MUL : basic_sse1_fp_binop_rm<0x59, "mul", fmul, int_x86_sse_mul_ss, 1>;
655 defm SUB : basic_sse1_fp_binop_rm<0x5C, "sub", fsub, int_x86_sse_sub_ss>;
656 defm DIV : basic_sse1_fp_binop_rm<0x5E, "div", fdiv, int_x86_sse_div_ss>;
657
658 /// sse1_fp_binop_rm - Other SSE1 binops
659 ///
660 /// This multiclass is like basic_sse1_fp_binop_rm, with the addition of
661 /// instructions for a full-vector intrinsic form.  Operations that map
662 /// onto C operators don't use this form since they just use the plain
663 /// vector form instead of having a separate vector intrinsic form.
664 ///
665 /// This provides a total of eight "instructions".
666 ///
667 let Constraints = "$src1 = $dst" in {
668 multiclass sse1_fp_binop_rm<bits<8> opc, string OpcodeStr,
669                             SDNode OpNode,
670                             Intrinsic F32Int,
671                             Intrinsic V4F32Int,
672                             bit Commutable = 0> {
673
674   // Scalar operation, reg+reg.
675   def SSrr : SSI<opc, MRMSrcReg, (outs FR32:$dst), (ins FR32:$src1, FR32:$src2),
676                  !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
677                  [(set FR32:$dst, (OpNode FR32:$src1, FR32:$src2))]> {
678     let isCommutable = Commutable;
679   }
680
681   // Scalar operation, reg+mem.
682   def SSrm : SSI<opc, MRMSrcMem, (outs FR32:$dst),
683                                  (ins FR32:$src1, f32mem:$src2),
684                  !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
685                  [(set FR32:$dst, (OpNode FR32:$src1, (load addr:$src2)))]>;
686
687   // Vector operation, reg+reg.
688   def PSrr : PSI<opc, MRMSrcReg, (outs VR128:$dst),
689                                  (ins VR128:$src1, VR128:$src2),
690                !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
691                [(set VR128:$dst, (v4f32 (OpNode VR128:$src1, VR128:$src2)))]> {
692     let isCommutable = Commutable;
693   }
694
695   // Vector operation, reg+mem.
696   def PSrm : PSI<opc, MRMSrcMem, (outs VR128:$dst),
697                                  (ins VR128:$src1, f128mem:$src2),
698                  !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
699              [(set VR128:$dst, (OpNode VR128:$src1, (memopv4f32 addr:$src2)))]>;
700
701   // Intrinsic operation, reg+reg.
702   def SSrr_Int : SSI<opc, MRMSrcReg, (outs VR128:$dst),
703                                      (ins VR128:$src1, VR128:$src2),
704                      !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
705                      [(set VR128:$dst, (F32Int VR128:$src1, VR128:$src2))]> {
706     let isCommutable = Commutable;
707   }
708
709   // Intrinsic operation, reg+mem.
710   def SSrm_Int : SSI<opc, MRMSrcMem, (outs VR128:$dst),
711                                      (ins VR128:$src1, ssmem:$src2),
712                      !strconcat(OpcodeStr, "ss\t{$src2, $dst|$dst, $src2}"),
713                      [(set VR128:$dst, (F32Int VR128:$src1,
714                                                sse_load_f32:$src2))]>;
715
716   // Vector intrinsic operation, reg+reg.
717   def PSrr_Int : PSI<opc, MRMSrcReg, (outs VR128:$dst),
718                                      (ins VR128:$src1, VR128:$src2),
719                      !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
720                      [(set VR128:$dst, (V4F32Int VR128:$src1, VR128:$src2))]> {
721     let isCommutable = Commutable;
722   }
723
724   // Vector intrinsic operation, reg+mem.
725   def PSrm_Int : PSI<opc, MRMSrcMem, (outs VR128:$dst),
726                                      (ins VR128:$src1, f128mem:$src2),
727                      !strconcat(OpcodeStr, "ps\t{$src2, $dst|$dst, $src2}"),
728            [(set VR128:$dst, (V4F32Int VR128:$src1, (memopv4f32 addr:$src2)))]>;
729 }
730 }
731
732 defm MAX : sse1_fp_binop_rm<0x5F, "max", X86fmax,
733                             int_x86_sse_max_ss, int_x86_sse_max_ps>;
734 defm MIN : sse1_fp_binop_rm<0x5D, "min", X86fmin,
735                             int_x86_sse_min_ss, int_x86_sse_min_ps>;
736
737 //===----------------------------------------------------------------------===//
738 // SSE packed FP Instructions
739
740 // Move Instructions
741 let neverHasSideEffects = 1 in
742 def MOVAPSrr : PSI<0x28, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
743                    "movaps\t{$src, $dst|$dst, $src}", []>;
744 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
745 def MOVAPSrm : PSI<0x28, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
746                    "movaps\t{$src, $dst|$dst, $src}",
747                    [(set VR128:$dst, (alignedloadv4f32 addr:$src))]>;
748
749 def MOVAPSmr : PSI<0x29, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
750                    "movaps\t{$src, $dst|$dst, $src}",
751                    [(alignedstore (v4f32 VR128:$src), addr:$dst)]>;
752
753 let neverHasSideEffects = 1 in
754 def MOVUPSrr : PSI<0x10, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
755                    "movups\t{$src, $dst|$dst, $src}", []>;
756 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
757 def MOVUPSrm : PSI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
758                    "movups\t{$src, $dst|$dst, $src}",
759                    [(set VR128:$dst, (loadv4f32 addr:$src))]>;
760 def MOVUPSmr : PSI<0x11, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
761                    "movups\t{$src, $dst|$dst, $src}",
762                    [(store (v4f32 VR128:$src), addr:$dst)]>;
763
764 // Intrinsic forms of MOVUPS load and store
765 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
766 def MOVUPSrm_Int : PSI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
767                        "movups\t{$src, $dst|$dst, $src}",
768                        [(set VR128:$dst, (int_x86_sse_loadu_ps addr:$src))]>;
769 def MOVUPSmr_Int : PSI<0x11, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
770                        "movups\t{$src, $dst|$dst, $src}",
771                        [(int_x86_sse_storeu_ps addr:$dst, VR128:$src)]>;
772
773 let Constraints = "$src1 = $dst" in {
774   let AddedComplexity = 20 in {
775     def MOVLPSrm : PSI<0x12, MRMSrcMem,
776                        (outs VR128:$dst), (ins VR128:$src1, f64mem:$src2),
777                        "movlps\t{$src2, $dst|$dst, $src2}",
778        [(set VR128:$dst,
779          (movlp VR128:$src1,
780                 (bc_v4f32 (v2f64 (scalar_to_vector (loadf64 addr:$src2))))))]>;
781     def MOVHPSrm : PSI<0x16, MRMSrcMem,
782                        (outs VR128:$dst), (ins VR128:$src1, f64mem:$src2),
783                        "movhps\t{$src2, $dst|$dst, $src2}",
784        [(set VR128:$dst,
785          (movlhps VR128:$src1,
786                 (bc_v4f32 (v2f64 (scalar_to_vector (loadf64 addr:$src2))))))]>;
787   } // AddedComplexity
788 } // Constraints = "$src1 = $dst"
789
790
791 def : Pat<(movlhps VR128:$src1, (bc_v4i32 (v2i64 (X86vzload addr:$src2)))),
792           (MOVHPSrm VR128:$src1, addr:$src2)>;
793
794 def MOVLPSmr : PSI<0x13, MRMDestMem, (outs), (ins f64mem:$dst, VR128:$src),
795                    "movlps\t{$src, $dst|$dst, $src}",
796                    [(store (f64 (vector_extract (bc_v2f64 (v4f32 VR128:$src)),
797                                  (iPTR 0))), addr:$dst)]>;
798
799 // v2f64 extract element 1 is always custom lowered to unpack high to low
800 // and extract element 0 so the non-store version isn't too horrible.
801 def MOVHPSmr : PSI<0x17, MRMDestMem, (outs), (ins f64mem:$dst, VR128:$src),
802                    "movhps\t{$src, $dst|$dst, $src}",
803                    [(store (f64 (vector_extract
804                                  (unpckh (bc_v2f64 (v4f32 VR128:$src)),
805                                          (undef)), (iPTR 0))), addr:$dst)]>;
806
807 let Constraints = "$src1 = $dst" in {
808 let AddedComplexity = 20 in {
809 def MOVLHPSrr : PSI<0x16, MRMSrcReg, (outs VR128:$dst),
810                                      (ins VR128:$src1, VR128:$src2),
811                     "movlhps\t{$src2, $dst|$dst, $src2}",
812                     [(set VR128:$dst,
813                       (v4f32 (movlhps VR128:$src1, VR128:$src2)))]>;
814
815 def MOVHLPSrr : PSI<0x12, MRMSrcReg, (outs VR128:$dst),
816                                      (ins VR128:$src1, VR128:$src2),
817                     "movhlps\t{$src2, $dst|$dst, $src2}",
818                     [(set VR128:$dst,
819                       (v4f32 (movhlps VR128:$src1, VR128:$src2)))]>;
820 } // AddedComplexity
821 } // Constraints = "$src1 = $dst"
822
823 let AddedComplexity = 20 in {
824 def : Pat<(v4f32 (movddup VR128:$src, (undef))),
825           (MOVLHPSrr VR128:$src, VR128:$src)>, Requires<[HasSSE1]>;
826 def : Pat<(v2i64 (movddup VR128:$src, (undef))),
827           (MOVLHPSrr VR128:$src, VR128:$src)>, Requires<[HasSSE1]>;
828 }
829
830
831
832 // Arithmetic
833
834 /// sse1_fp_unop_rm - SSE1 unops come in both scalar and vector forms.
835 ///
836 /// In addition, we also have a special variant of the scalar form here to
837 /// represent the associated intrinsic operation.  This form is unlike the
838 /// plain scalar form, in that it takes an entire vector (instead of a
839 /// scalar) and leaves the top elements undefined.
840 ///
841 /// And, we have a special variant form for a full-vector intrinsic form.
842 ///
843 /// These four forms can each have a reg or a mem operand, so there are a
844 /// total of eight "instructions".
845 ///
846 multiclass sse1_fp_unop_rm<bits<8> opc, string OpcodeStr,
847                            SDNode OpNode,
848                            Intrinsic F32Int,
849                            Intrinsic V4F32Int,
850                            bit Commutable = 0> {
851   // Scalar operation, reg.
852   def SSr : SSI<opc, MRMSrcReg, (outs FR32:$dst), (ins FR32:$src),
853                 !strconcat(OpcodeStr, "ss\t{$src, $dst|$dst, $src}"),
854                 [(set FR32:$dst, (OpNode FR32:$src))]> {
855     let isCommutable = Commutable;
856   }
857
858   // Scalar operation, mem.
859   def SSm : I<opc, MRMSrcMem, (outs FR32:$dst), (ins f32mem:$src),
860                 !strconcat(OpcodeStr, "ss\t{$src, $dst|$dst, $src}"),
861                 [(set FR32:$dst, (OpNode (load addr:$src)))]>, XS,
862             Requires<[HasSSE1, OptForSize]>;
863
864   // Vector operation, reg.
865   def PSr : PSI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
866               !strconcat(OpcodeStr, "ps\t{$src, $dst|$dst, $src}"),
867               [(set VR128:$dst, (v4f32 (OpNode VR128:$src)))]> {
868     let isCommutable = Commutable;
869   }
870
871   // Vector operation, mem.
872   def PSm : PSI<opc, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
873                 !strconcat(OpcodeStr, "ps\t{$src, $dst|$dst, $src}"),
874                 [(set VR128:$dst, (OpNode (memopv4f32 addr:$src)))]>;
875
876   // Intrinsic operation, reg.
877   def SSr_Int : SSI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
878                     !strconcat(OpcodeStr, "ss\t{$src, $dst|$dst, $src}"),
879                     [(set VR128:$dst, (F32Int VR128:$src))]> {
880     let isCommutable = Commutable;
881   }
882
883   // Intrinsic operation, mem.
884   def SSm_Int : SSI<opc, MRMSrcMem, (outs VR128:$dst), (ins ssmem:$src),
885                     !strconcat(OpcodeStr, "ss\t{$src, $dst|$dst, $src}"),
886                     [(set VR128:$dst, (F32Int sse_load_f32:$src))]>;
887
888   // Vector intrinsic operation, reg
889   def PSr_Int : PSI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
890                     !strconcat(OpcodeStr, "ps\t{$src, $dst|$dst, $src}"),
891                     [(set VR128:$dst, (V4F32Int VR128:$src))]> {
892     let isCommutable = Commutable;
893   }
894
895   // Vector intrinsic operation, mem
896   def PSm_Int : PSI<opc, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
897                     !strconcat(OpcodeStr, "ps\t{$src, $dst|$dst, $src}"),
898                     [(set VR128:$dst, (V4F32Int (memopv4f32 addr:$src)))]>;
899 }
900
901 // Square root.
902 defm SQRT  : sse1_fp_unop_rm<0x51, "sqrt",  fsqrt,
903                              int_x86_sse_sqrt_ss, int_x86_sse_sqrt_ps>;
904
905 // Reciprocal approximations. Note that these typically require refinement
906 // in order to obtain suitable precision.
907 defm RSQRT : sse1_fp_unop_rm<0x52, "rsqrt", X86frsqrt,
908                              int_x86_sse_rsqrt_ss, int_x86_sse_rsqrt_ps>;
909 defm RCP   : sse1_fp_unop_rm<0x53, "rcp",   X86frcp,
910                              int_x86_sse_rcp_ss, int_x86_sse_rcp_ps>;
911
912 // Logical
913 let Constraints = "$src1 = $dst" in {
914   let isCommutable = 1 in {
915     def ANDPSrr : PSI<0x54, MRMSrcReg,
916                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
917                       "andps\t{$src2, $dst|$dst, $src2}",
918                       [(set VR128:$dst, (v2i64
919                                          (and VR128:$src1, VR128:$src2)))]>;
920     def ORPSrr  : PSI<0x56, MRMSrcReg,
921                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
922                       "orps\t{$src2, $dst|$dst, $src2}",
923                       [(set VR128:$dst, (v2i64
924                                          (or VR128:$src1, VR128:$src2)))]>;
925     def XORPSrr : PSI<0x57, MRMSrcReg,
926                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
927                       "xorps\t{$src2, $dst|$dst, $src2}",
928                       [(set VR128:$dst, (v2i64
929                                          (xor VR128:$src1, VR128:$src2)))]>;
930   }
931
932   def ANDPSrm : PSI<0x54, MRMSrcMem,
933                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
934                     "andps\t{$src2, $dst|$dst, $src2}",
935                     [(set VR128:$dst, (and (bc_v2i64 (v4f32 VR128:$src1)),
936                                        (memopv2i64 addr:$src2)))]>;
937   def ORPSrm  : PSI<0x56, MRMSrcMem,
938                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
939                     "orps\t{$src2, $dst|$dst, $src2}",
940                     [(set VR128:$dst, (or (bc_v2i64 (v4f32 VR128:$src1)),
941                                        (memopv2i64 addr:$src2)))]>;
942   def XORPSrm : PSI<0x57, MRMSrcMem,
943                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
944                     "xorps\t{$src2, $dst|$dst, $src2}",
945                     [(set VR128:$dst, (xor (bc_v2i64 (v4f32 VR128:$src1)),
946                                        (memopv2i64 addr:$src2)))]>;
947   def ANDNPSrr : PSI<0x55, MRMSrcReg,
948                      (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
949                      "andnps\t{$src2, $dst|$dst, $src2}",
950                      [(set VR128:$dst,
951                        (v2i64 (and (xor VR128:$src1,
952                                     (bc_v2i64 (v4i32 immAllOnesV))),
953                                VR128:$src2)))]>;
954   def ANDNPSrm : PSI<0x55, MRMSrcMem,
955                      (outs VR128:$dst), (ins VR128:$src1,f128mem:$src2),
956                      "andnps\t{$src2, $dst|$dst, $src2}",
957                      [(set VR128:$dst,
958                        (v2i64 (and (xor (bc_v2i64 (v4f32 VR128:$src1)),
959                                     (bc_v2i64 (v4i32 immAllOnesV))),
960                                (memopv2i64 addr:$src2))))]>;
961 }
962
963 let Constraints = "$src1 = $dst" in {
964   def CMPPSrri : PSIi8<0xC2, MRMSrcReg,
965                     (outs VR128:$dst), (ins VR128:$src1, VR128:$src, SSECC:$cc),
966                     "cmp${cc}ps\t{$src, $dst|$dst, $src}",
967                     [(set VR128:$dst, (int_x86_sse_cmp_ps VR128:$src1,
968                                                         VR128:$src, imm:$cc))]>;
969   def CMPPSrmi : PSIi8<0xC2, MRMSrcMem,
970                   (outs VR128:$dst), (ins VR128:$src1, f128mem:$src, SSECC:$cc),
971                   "cmp${cc}ps\t{$src, $dst|$dst, $src}",
972                   [(set VR128:$dst, (int_x86_sse_cmp_ps VR128:$src1,
973                                             (memop addr:$src), imm:$cc))]>;
974 }
975 def : Pat<(v4i32 (X86cmpps (v4f32 VR128:$src1), VR128:$src2, imm:$cc)),
976           (CMPPSrri VR128:$src1, VR128:$src2, imm:$cc)>;
977 def : Pat<(v4i32 (X86cmpps (v4f32 VR128:$src1), (memop addr:$src2), imm:$cc)),
978           (CMPPSrmi VR128:$src1, addr:$src2, imm:$cc)>;
979
980 // Shuffle and unpack instructions
981 let Constraints = "$src1 = $dst" in {
982   let isConvertibleToThreeAddress = 1 in // Convert to pshufd
983     def SHUFPSrri : PSIi8<0xC6, MRMSrcReg,
984                           (outs VR128:$dst), (ins VR128:$src1,
985                            VR128:$src2, i8imm:$src3),
986                           "shufps\t{$src3, $src2, $dst|$dst, $src2, $src3}",
987                           [(set VR128:$dst,
988                             (v4f32 (shufp:$src3 VR128:$src1, VR128:$src2)))]>;
989   def SHUFPSrmi : PSIi8<0xC6, MRMSrcMem,
990                         (outs VR128:$dst), (ins VR128:$src1,
991                          f128mem:$src2, i8imm:$src3),
992                         "shufps\t{$src3, $src2, $dst|$dst, $src2, $src3}",
993                         [(set VR128:$dst,
994                           (v4f32 (shufp:$src3
995                                   VR128:$src1, (memopv4f32 addr:$src2))))]>;
996
997   let AddedComplexity = 10 in {
998     def UNPCKHPSrr : PSI<0x15, MRMSrcReg,
999                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1000                          "unpckhps\t{$src2, $dst|$dst, $src2}",
1001                          [(set VR128:$dst,
1002                            (v4f32 (unpckh VR128:$src1, VR128:$src2)))]>;
1003     def UNPCKHPSrm : PSI<0x15, MRMSrcMem,
1004                          (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1005                          "unpckhps\t{$src2, $dst|$dst, $src2}",
1006                          [(set VR128:$dst,
1007                            (v4f32 (unpckh VR128:$src1,
1008                                           (memopv4f32 addr:$src2))))]>;
1009
1010     def UNPCKLPSrr : PSI<0x14, MRMSrcReg,
1011                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1012                          "unpcklps\t{$src2, $dst|$dst, $src2}",
1013                          [(set VR128:$dst,
1014                            (v4f32 (unpckl VR128:$src1, VR128:$src2)))]>;
1015     def UNPCKLPSrm : PSI<0x14, MRMSrcMem,
1016                          (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1017                          "unpcklps\t{$src2, $dst|$dst, $src2}",
1018                          [(set VR128:$dst,
1019                            (unpckl VR128:$src1, (memopv4f32 addr:$src2)))]>;
1020   } // AddedComplexity
1021 } // Constraints = "$src1 = $dst"
1022
1023 // Mask creation
1024 def MOVMSKPSrr : PSI<0x50, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
1025                      "movmskps\t{$src, $dst|$dst, $src}",
1026                      [(set GR32:$dst, (int_x86_sse_movmsk_ps VR128:$src))]>;
1027 def MOVMSKPDrr : PDI<0x50, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
1028                      "movmskpd\t{$src, $dst|$dst, $src}",
1029                      [(set GR32:$dst, (int_x86_sse2_movmsk_pd VR128:$src))]>;
1030
1031 // Prefetch intrinsic.
1032 def PREFETCHT0   : PSI<0x18, MRM1m, (outs), (ins i8mem:$src),
1033     "prefetcht0\t$src", [(prefetch addr:$src, imm, (i32 3))]>;
1034 def PREFETCHT1   : PSI<0x18, MRM2m, (outs), (ins i8mem:$src),
1035     "prefetcht1\t$src", [(prefetch addr:$src, imm, (i32 2))]>;
1036 def PREFETCHT2   : PSI<0x18, MRM3m, (outs), (ins i8mem:$src),
1037     "prefetcht2\t$src", [(prefetch addr:$src, imm, (i32 1))]>;
1038 def PREFETCHNTA  : PSI<0x18, MRM0m, (outs), (ins i8mem:$src),
1039     "prefetchnta\t$src", [(prefetch addr:$src, imm, (i32 0))]>;
1040
1041 // Non-temporal stores
1042 def MOVNTPSmr_Int : PSI<0x2B, MRMDestMem, (outs), (ins i128mem:$dst, VR128:$src),
1043                     "movntps\t{$src, $dst|$dst, $src}",
1044                     [(int_x86_sse_movnt_ps addr:$dst, VR128:$src)]>;
1045
1046 let AddedComplexity = 400 in { // Prefer non-temporal versions
1047 def MOVNTPSmr : PSI<0x2B, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
1048                     "movntps\t{$src, $dst|$dst, $src}",
1049                     [(alignednontemporalstore (v4f32 VR128:$src), addr:$dst)]>;
1050
1051 def MOVNTDQ_64mr : PDI<0xE7, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
1052                     "movntdq\t{$src, $dst|$dst, $src}",
1053                     [(alignednontemporalstore (v2f64 VR128:$src), addr:$dst)]>;
1054
1055 def : Pat<(alignednontemporalstore (v2i64 VR128:$src), addr:$dst),
1056           (MOVNTDQ_64mr VR128:$src, addr:$dst)>;
1057
1058 def MOVNTImr : I<0xC3, MRMDestMem, (outs), (ins i32mem:$dst, GR32:$src),
1059                  "movnti\t{$src, $dst|$dst, $src}",
1060                  [(nontemporalstore (i32 GR32:$src), addr:$dst)]>,
1061                TB, Requires<[HasSSE2]>;
1062
1063 def MOVNTI_64mr : RI<0xC3, MRMDestMem, (outs), (ins i64mem:$dst, GR64:$src),
1064                      "movnti\t{$src, $dst|$dst, $src}",
1065                      [(nontemporalstore (i64 GR64:$src), addr:$dst)]>,
1066                   TB, Requires<[HasSSE2]>;
1067 }
1068
1069 // Load, store, and memory fence
1070 def SFENCE : PSI<0xAE, MRM7r, (outs), (ins), "sfence", [(int_x86_sse_sfence)]>;
1071
1072 // MXCSR register
1073 def LDMXCSR : PSI<0xAE, MRM2m, (outs), (ins i32mem:$src),
1074                   "ldmxcsr\t$src", [(int_x86_sse_ldmxcsr addr:$src)]>;
1075 def STMXCSR : PSI<0xAE, MRM3m, (outs), (ins i32mem:$dst),
1076                   "stmxcsr\t$dst", [(int_x86_sse_stmxcsr addr:$dst)]>;
1077
1078 // Alias instructions that map zero vector to pxor / xorp* for sse.
1079 // We set canFoldAsLoad because this can be converted to a constant-pool
1080 // load of an all-zeros value if folding it would be beneficial.
1081 // FIXME: Change encoding to pseudo!
1082 let isReMaterializable = 1, isAsCheapAsAMove = 1, canFoldAsLoad = 1,
1083     isCodeGenOnly = 1 in
1084 def V_SET0 : PSI<0x57, MRMInitReg, (outs VR128:$dst), (ins), "",
1085                  [(set VR128:$dst, (v4i32 immAllZerosV))]>;
1086
1087 let Predicates = [HasSSE1] in {
1088   def : Pat<(v2i64 immAllZerosV), (V_SET0)>;
1089   def : Pat<(v8i16 immAllZerosV), (V_SET0)>;
1090   def : Pat<(v16i8 immAllZerosV), (V_SET0)>;
1091   def : Pat<(v2f64 immAllZerosV), (V_SET0)>;
1092   def : Pat<(v4f32 immAllZerosV), (V_SET0)>;
1093 }
1094
1095 // FR32 to 128-bit vector conversion.
1096 let isAsCheapAsAMove = 1 in
1097 def MOVSS2PSrr : SSI<0x10, MRMSrcReg, (outs VR128:$dst), (ins FR32:$src),
1098                       "movss\t{$src, $dst|$dst, $src}",
1099                       [(set VR128:$dst,
1100                         (v4f32 (scalar_to_vector FR32:$src)))]>;
1101 def MOVSS2PSrm : SSI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f32mem:$src),
1102                      "movss\t{$src, $dst|$dst, $src}",
1103                      [(set VR128:$dst,
1104                        (v4f32 (scalar_to_vector (loadf32 addr:$src))))]>;
1105
1106 // FIXME: may not be able to eliminate this movss with coalescing the src and
1107 // dest register classes are different. We really want to write this pattern
1108 // like this:
1109 // def : Pat<(f32 (vector_extract (v4f32 VR128:$src), (iPTR 0))),
1110 //           (f32 FR32:$src)>;
1111 let isAsCheapAsAMove = 1 in
1112 def MOVPS2SSrr : SSI<0x10, MRMSrcReg, (outs FR32:$dst), (ins VR128:$src),
1113                      "movss\t{$src, $dst|$dst, $src}",
1114                      [(set FR32:$dst, (vector_extract (v4f32 VR128:$src),
1115                                        (iPTR 0)))]>;
1116 def MOVPS2SSmr : SSI<0x11, MRMDestMem, (outs), (ins f32mem:$dst, VR128:$src),
1117                      "movss\t{$src, $dst|$dst, $src}",
1118                      [(store (f32 (vector_extract (v4f32 VR128:$src),
1119                                    (iPTR 0))), addr:$dst)]>;
1120
1121
1122 // Move to lower bits of a VR128, leaving upper bits alone.
1123 // Three operand (but two address) aliases.
1124 let Constraints = "$src1 = $dst" in {
1125 let neverHasSideEffects = 1 in
1126   def MOVLSS2PSrr : SSI<0x10, MRMSrcReg,
1127                         (outs VR128:$dst), (ins VR128:$src1, FR32:$src2),
1128                         "movss\t{$src2, $dst|$dst, $src2}", []>;
1129
1130   let AddedComplexity = 15 in
1131     def MOVLPSrr : SSI<0x10, MRMSrcReg,
1132                        (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1133                        "movss\t{$src2, $dst|$dst, $src2}",
1134                        [(set VR128:$dst,
1135                          (v4f32 (movl VR128:$src1, VR128:$src2)))]>;
1136 }
1137
1138 // Move to lower bits of a VR128 and zeroing upper bits.
1139 // Loading from memory automatically zeroing upper bits.
1140 let AddedComplexity = 20 in
1141 def MOVZSS2PSrm : SSI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f32mem:$src),
1142                       "movss\t{$src, $dst|$dst, $src}",
1143                    [(set VR128:$dst, (v4f32 (X86vzmovl (v4f32 (scalar_to_vector
1144                                                     (loadf32 addr:$src))))))]>;
1145
1146 def : Pat<(v4f32 (X86vzmovl (loadv4f32 addr:$src))),
1147           (MOVZSS2PSrm addr:$src)>;
1148
1149 //===---------------------------------------------------------------------===//
1150 // SSE2 Instructions
1151 //===---------------------------------------------------------------------===//
1152
1153 // Move Instructions
1154 let neverHasSideEffects = 1 in
1155 def MOVSDrr : SDI<0x10, MRMSrcReg, (outs FR64:$dst), (ins FR64:$src),
1156                   "movsd\t{$src, $dst|$dst, $src}", []>;
1157 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
1158 def MOVSDrm : SDI<0x10, MRMSrcMem, (outs FR64:$dst), (ins f64mem:$src),
1159                   "movsd\t{$src, $dst|$dst, $src}",
1160                   [(set FR64:$dst, (loadf64 addr:$src))]>;
1161 def MOVSDmr : SDI<0x11, MRMDestMem, (outs), (ins f64mem:$dst, FR64:$src),
1162                   "movsd\t{$src, $dst|$dst, $src}",
1163                   [(store FR64:$src, addr:$dst)]>;
1164
1165 // Conversion instructions
1166 def CVTTSD2SIrr : SDI<0x2C, MRMSrcReg, (outs GR32:$dst), (ins FR64:$src),
1167                       "cvttsd2si\t{$src, $dst|$dst, $src}",
1168                       [(set GR32:$dst, (fp_to_sint FR64:$src))]>;
1169 def CVTTSD2SIrm : SDI<0x2C, MRMSrcMem, (outs GR32:$dst), (ins f64mem:$src),
1170                       "cvttsd2si\t{$src, $dst|$dst, $src}",
1171                       [(set GR32:$dst, (fp_to_sint (loadf64 addr:$src)))]>;
1172 def CVTSD2SSrr  : SDI<0x5A, MRMSrcReg, (outs FR32:$dst), (ins FR64:$src),
1173                       "cvtsd2ss\t{$src, $dst|$dst, $src}",
1174                       [(set FR32:$dst, (fround FR64:$src))]>;
1175 def CVTSD2SSrm  : I<0x5A, MRMSrcMem, (outs FR32:$dst), (ins f64mem:$src),
1176                       "cvtsd2ss\t{$src, $dst|$dst, $src}",
1177                       [(set FR32:$dst, (fround (loadf64 addr:$src)))]>, XD,
1178                   Requires<[HasSSE2, OptForSize]>;
1179 def CVTSI2SDrr  : SDI<0x2A, MRMSrcReg, (outs FR64:$dst), (ins GR32:$src),
1180                       "cvtsi2sd\t{$src, $dst|$dst, $src}",
1181                       [(set FR64:$dst, (sint_to_fp GR32:$src))]>;
1182 def CVTSI2SDrm  : SDI<0x2A, MRMSrcMem, (outs FR64:$dst), (ins i32mem:$src),
1183                       "cvtsi2sd\t{$src, $dst|$dst, $src}",
1184                       [(set FR64:$dst, (sint_to_fp (loadi32 addr:$src)))]>;
1185
1186 def CVTPD2DQrm  : S3DI<0xE6, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1187                        "cvtpd2dq\t{$src, $dst|$dst, $src}", []>;
1188 def CVTPD2DQrr  : S3DI<0xE6, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1189                        "cvtpd2dq\t{$src, $dst|$dst, $src}", []>;
1190 def CVTDQ2PDrm  : S3SI<0xE6, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1191                        "cvtdq2pd\t{$src, $dst|$dst, $src}", []>;
1192 def CVTDQ2PDrr  : S3SI<0xE6, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1193                        "cvtdq2pd\t{$src, $dst|$dst, $src}", []>;
1194 def CVTPS2DQrr : PDI<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1195                      "cvtps2dq\t{$src, $dst|$dst, $src}", []>;
1196 def CVTPS2DQrm : PDI<0x5B, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1197                      "cvtps2dq\t{$src, $dst|$dst, $src}", []>;
1198 def CVTDQ2PSrr : PSI<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1199                      "cvtdq2ps\t{$src, $dst|$dst, $src}", []>;
1200 def CVTDQ2PSrm : PSI<0x5B, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1201                      "cvtdq2ps\t{$src, $dst|$dst, $src}", []>;
1202 def COMISDrr: PDI<0x2F, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
1203                   "comisd\t{$src2, $src1|$src1, $src2}", []>;
1204 def COMISDrm: PDI<0x2F, MRMSrcMem, (outs), (ins VR128:$src1, f128mem:$src2),
1205                       "comisd\t{$src2, $src1|$src1, $src2}", []>;
1206
1207 // SSE2 instructions with XS prefix
1208 def CVTSS2SDrr : I<0x5A, MRMSrcReg, (outs FR64:$dst), (ins FR32:$src),
1209                    "cvtss2sd\t{$src, $dst|$dst, $src}",
1210                    [(set FR64:$dst, (fextend FR32:$src))]>, XS,
1211                  Requires<[HasSSE2]>;
1212 def CVTSS2SDrm : I<0x5A, MRMSrcMem, (outs FR64:$dst), (ins f32mem:$src),
1213                    "cvtss2sd\t{$src, $dst|$dst, $src}",
1214                    [(set FR64:$dst, (extloadf32 addr:$src))]>, XS,
1215                  Requires<[HasSSE2, OptForSize]>;
1216
1217 def : Pat<(extloadf32 addr:$src),
1218           (CVTSS2SDrr (MOVSSrm addr:$src))>, Requires<[HasSSE2, OptForSpeed]>;
1219
1220 // Match intrinsics which expect XMM operand(s).
1221 def Int_CVTSD2SIrr : SDI<0x2D, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
1222                          "cvtsd2si\t{$src, $dst|$dst, $src}",
1223                          [(set GR32:$dst, (int_x86_sse2_cvtsd2si VR128:$src))]>;
1224 def Int_CVTSD2SIrm : SDI<0x2D, MRMSrcMem, (outs GR32:$dst), (ins f128mem:$src),
1225                          "cvtsd2si\t{$src, $dst|$dst, $src}",
1226                          [(set GR32:$dst, (int_x86_sse2_cvtsd2si
1227                                            (load addr:$src)))]>;
1228
1229 // Match intrinisics which expect MM and XMM operand(s).
1230 def Int_CVTPD2PIrr : PDI<0x2D, MRMSrcReg, (outs VR64:$dst), (ins VR128:$src),
1231                          "cvtpd2pi\t{$src, $dst|$dst, $src}",
1232                          [(set VR64:$dst, (int_x86_sse_cvtpd2pi VR128:$src))]>;
1233 def Int_CVTPD2PIrm : PDI<0x2D, MRMSrcMem, (outs VR64:$dst), (ins f128mem:$src),
1234                          "cvtpd2pi\t{$src, $dst|$dst, $src}",
1235                          [(set VR64:$dst, (int_x86_sse_cvtpd2pi
1236                                            (memop addr:$src)))]>;
1237 def Int_CVTTPD2PIrr: PDI<0x2C, MRMSrcReg, (outs VR64:$dst), (ins VR128:$src),
1238                          "cvttpd2pi\t{$src, $dst|$dst, $src}",
1239                          [(set VR64:$dst, (int_x86_sse_cvttpd2pi VR128:$src))]>;
1240 def Int_CVTTPD2PIrm: PDI<0x2C, MRMSrcMem, (outs VR64:$dst), (ins f128mem:$src),
1241                          "cvttpd2pi\t{$src, $dst|$dst, $src}",
1242                          [(set VR64:$dst, (int_x86_sse_cvttpd2pi
1243                                            (memop addr:$src)))]>;
1244 def Int_CVTPI2PDrr : PDI<0x2A, MRMSrcReg, (outs VR128:$dst), (ins VR64:$src),
1245                          "cvtpi2pd\t{$src, $dst|$dst, $src}",
1246                          [(set VR128:$dst, (int_x86_sse_cvtpi2pd VR64:$src))]>;
1247 def Int_CVTPI2PDrm : PDI<0x2A, MRMSrcMem, (outs VR128:$dst), (ins i64mem:$src),
1248                          "cvtpi2pd\t{$src, $dst|$dst, $src}",
1249                          [(set VR128:$dst, (int_x86_sse_cvtpi2pd
1250                                             (load addr:$src)))]>;
1251
1252 // Aliases for intrinsics
1253 def Int_CVTTSD2SIrr : SDI<0x2C, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
1254                           "cvttsd2si\t{$src, $dst|$dst, $src}",
1255                           [(set GR32:$dst,
1256                             (int_x86_sse2_cvttsd2si VR128:$src))]>;
1257 def Int_CVTTSD2SIrm : SDI<0x2C, MRMSrcMem, (outs GR32:$dst), (ins f128mem:$src),
1258                           "cvttsd2si\t{$src, $dst|$dst, $src}",
1259                           [(set GR32:$dst, (int_x86_sse2_cvttsd2si
1260                                             (load addr:$src)))]>;
1261
1262 // Comparison instructions
1263 let Constraints = "$src1 = $dst", neverHasSideEffects = 1 in {
1264   def CMPSDrr : SDIi8<0xC2, MRMSrcReg,
1265                     (outs FR64:$dst), (ins FR64:$src1, FR64:$src, SSECC:$cc),
1266                     "cmp${cc}sd\t{$src, $dst|$dst, $src}", []>;
1267 let mayLoad = 1 in
1268   def CMPSDrm : SDIi8<0xC2, MRMSrcMem,
1269                     (outs FR64:$dst), (ins FR64:$src1, f64mem:$src, SSECC:$cc),
1270                     "cmp${cc}sd\t{$src, $dst|$dst, $src}", []>;
1271 }
1272
1273 let Defs = [EFLAGS] in {
1274 def UCOMISDrr: PDI<0x2E, MRMSrcReg, (outs), (ins FR64:$src1, FR64:$src2),
1275                    "ucomisd\t{$src2, $src1|$src1, $src2}",
1276                    [(X86cmp FR64:$src1, FR64:$src2), (implicit EFLAGS)]>;
1277 def UCOMISDrm: PDI<0x2E, MRMSrcMem, (outs), (ins FR64:$src1, f64mem:$src2),
1278                    "ucomisd\t{$src2, $src1|$src1, $src2}",
1279                    [(X86cmp FR64:$src1, (loadf64 addr:$src2)),
1280                     (implicit EFLAGS)]>;
1281 } // Defs = [EFLAGS]
1282
1283 // Aliases to match intrinsics which expect XMM operand(s).
1284 let Constraints = "$src1 = $dst" in {
1285   def Int_CMPSDrr : SDIi8<0xC2, MRMSrcReg,
1286                         (outs VR128:$dst), 
1287                         (ins VR128:$src1, VR128:$src, SSECC:$cc),
1288                         "cmp${cc}sd\t{$src, $dst|$dst, $src}",
1289                         [(set VR128:$dst, (int_x86_sse2_cmp_sd VR128:$src1,
1290                                            VR128:$src, imm:$cc))]>;
1291   def Int_CMPSDrm : SDIi8<0xC2, MRMSrcMem,
1292                         (outs VR128:$dst), 
1293                         (ins VR128:$src1, f64mem:$src, SSECC:$cc),
1294                         "cmp${cc}sd\t{$src, $dst|$dst, $src}",
1295                         [(set VR128:$dst, (int_x86_sse2_cmp_sd VR128:$src1,
1296                                            (load addr:$src), imm:$cc))]>;
1297 }
1298
1299 let Defs = [EFLAGS] in {
1300 def Int_UCOMISDrr: PDI<0x2E, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
1301                        "ucomisd\t{$src2, $src1|$src1, $src2}",
1302                        [(X86ucomi (v2f64 VR128:$src1), (v2f64 VR128:$src2)),
1303                         (implicit EFLAGS)]>;
1304 def Int_UCOMISDrm: PDI<0x2E, MRMSrcMem, (outs),(ins VR128:$src1, f128mem:$src2),
1305                        "ucomisd\t{$src2, $src1|$src1, $src2}",
1306                        [(X86ucomi (v2f64 VR128:$src1), (load addr:$src2)),
1307                         (implicit EFLAGS)]>;
1308
1309 def Int_COMISDrr: PDI<0x2F, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
1310                       "comisd\t{$src2, $src1|$src1, $src2}",
1311                       [(X86comi (v2f64 VR128:$src1), (v2f64 VR128:$src2)),
1312                        (implicit EFLAGS)]>;
1313 def Int_COMISDrm: PDI<0x2F, MRMSrcMem, (outs), (ins VR128:$src1, f128mem:$src2),
1314                       "comisd\t{$src2, $src1|$src1, $src2}",
1315                       [(X86comi (v2f64 VR128:$src1), (load addr:$src2)),
1316                        (implicit EFLAGS)]>;
1317 } // Defs = [EFLAGS]
1318
1319 // Aliases of packed SSE2 instructions for scalar use. These all have names
1320 // that start with 'Fs'.
1321
1322 // Alias instructions that map fld0 to pxor for sse.
1323 let isReMaterializable = 1, isAsCheapAsAMove = 1, isCodeGenOnly = 1,
1324     canFoldAsLoad = 1 in
1325 def FsFLD0SD : I<0xEF, MRMInitReg, (outs FR64:$dst), (ins), "",
1326                  [(set FR64:$dst, fpimm0)]>,
1327                Requires<[HasSSE2]>, TB, OpSize;
1328
1329 // Alias instruction to do FR64 reg-to-reg copy using movapd. Upper bits are
1330 // disregarded.
1331 let neverHasSideEffects = 1 in
1332 def FsMOVAPDrr : PDI<0x28, MRMSrcReg, (outs FR64:$dst), (ins FR64:$src),
1333                      "movapd\t{$src, $dst|$dst, $src}", []>;
1334
1335 // Alias instruction to load FR64 from f128mem using movapd. Upper bits are
1336 // disregarded.
1337 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
1338 def FsMOVAPDrm : PDI<0x28, MRMSrcMem, (outs FR64:$dst), (ins f128mem:$src),
1339                      "movapd\t{$src, $dst|$dst, $src}",
1340                      [(set FR64:$dst, (alignedloadfsf64 addr:$src))]>;
1341
1342 // Alias bitwise logical operations using SSE logical ops on packed FP values.
1343 let Constraints = "$src1 = $dst" in {
1344 let isCommutable = 1 in {
1345   def FsANDPDrr : PDI<0x54, MRMSrcReg, (outs FR64:$dst),
1346                                        (ins FR64:$src1, FR64:$src2),
1347                       "andpd\t{$src2, $dst|$dst, $src2}",
1348                       [(set FR64:$dst, (X86fand FR64:$src1, FR64:$src2))]>;
1349   def FsORPDrr  : PDI<0x56, MRMSrcReg, (outs FR64:$dst),
1350                                        (ins FR64:$src1, FR64:$src2),
1351                       "orpd\t{$src2, $dst|$dst, $src2}",
1352                       [(set FR64:$dst, (X86for FR64:$src1, FR64:$src2))]>;
1353   def FsXORPDrr : PDI<0x57, MRMSrcReg, (outs FR64:$dst),
1354                                        (ins FR64:$src1, FR64:$src2),
1355                       "xorpd\t{$src2, $dst|$dst, $src2}",
1356                       [(set FR64:$dst, (X86fxor FR64:$src1, FR64:$src2))]>;
1357 }
1358
1359 def FsANDPDrm : PDI<0x54, MRMSrcMem, (outs FR64:$dst),
1360                                      (ins FR64:$src1, f128mem:$src2),
1361                     "andpd\t{$src2, $dst|$dst, $src2}",
1362                     [(set FR64:$dst, (X86fand FR64:$src1,
1363                                       (memopfsf64 addr:$src2)))]>;
1364 def FsORPDrm  : PDI<0x56, MRMSrcMem, (outs FR64:$dst),
1365                                      (ins FR64:$src1, f128mem:$src2),
1366                     "orpd\t{$src2, $dst|$dst, $src2}",
1367                     [(set FR64:$dst, (X86for FR64:$src1,
1368                                       (memopfsf64 addr:$src2)))]>;
1369 def FsXORPDrm : PDI<0x57, MRMSrcMem, (outs FR64:$dst),
1370                                      (ins FR64:$src1, f128mem:$src2),
1371                     "xorpd\t{$src2, $dst|$dst, $src2}",
1372                     [(set FR64:$dst, (X86fxor FR64:$src1,
1373                                       (memopfsf64 addr:$src2)))]>;
1374
1375 let neverHasSideEffects = 1 in {
1376 def FsANDNPDrr : PDI<0x55, MRMSrcReg,
1377                      (outs FR64:$dst), (ins FR64:$src1, FR64:$src2),
1378                      "andnpd\t{$src2, $dst|$dst, $src2}", []>;
1379 let mayLoad = 1 in
1380 def FsANDNPDrm : PDI<0x55, MRMSrcMem,
1381                      (outs FR64:$dst), (ins FR64:$src1, f128mem:$src2),
1382                      "andnpd\t{$src2, $dst|$dst, $src2}", []>;
1383 }
1384 }
1385
1386 /// basic_sse2_fp_binop_rm - SSE2 binops come in both scalar and vector forms.
1387 ///
1388 /// In addition, we also have a special variant of the scalar form here to
1389 /// represent the associated intrinsic operation.  This form is unlike the
1390 /// plain scalar form, in that it takes an entire vector (instead of a scalar)
1391 /// and leaves the top elements unmodified (therefore these cannot be commuted).
1392 ///
1393 /// These three forms can each be reg+reg or reg+mem, so there are a total of
1394 /// six "instructions".
1395 ///
1396 let Constraints = "$src1 = $dst" in {
1397 multiclass basic_sse2_fp_binop_rm<bits<8> opc, string OpcodeStr,
1398                                   SDNode OpNode, Intrinsic F64Int,
1399                                   bit Commutable = 0> {
1400   // Scalar operation, reg+reg.
1401   def SDrr : SDI<opc, MRMSrcReg, (outs FR64:$dst), (ins FR64:$src1, FR64:$src2),
1402                  !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1403                  [(set FR64:$dst, (OpNode FR64:$src1, FR64:$src2))]> {
1404     let isCommutable = Commutable;
1405   }
1406
1407   // Scalar operation, reg+mem.
1408   def SDrm : SDI<opc, MRMSrcMem, (outs FR64:$dst),
1409                                  (ins FR64:$src1, f64mem:$src2),
1410                  !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1411                  [(set FR64:$dst, (OpNode FR64:$src1, (load addr:$src2)))]>;
1412
1413   // Vector operation, reg+reg.
1414   def PDrr : PDI<opc, MRMSrcReg, (outs VR128:$dst),
1415                                  (ins VR128:$src1, VR128:$src2),
1416                !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1417                [(set VR128:$dst, (v2f64 (OpNode VR128:$src1, VR128:$src2)))]> {
1418     let isCommutable = Commutable;
1419   }
1420
1421   // Vector operation, reg+mem.
1422   def PDrm : PDI<opc, MRMSrcMem, (outs VR128:$dst),
1423                                  (ins VR128:$src1, f128mem:$src2),
1424                  !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1425              [(set VR128:$dst, (OpNode VR128:$src1, (memopv2f64 addr:$src2)))]>;
1426
1427   // Intrinsic operation, reg+reg.
1428   def SDrr_Int : SDI<opc, MRMSrcReg, (outs VR128:$dst),
1429                                      (ins VR128:$src1, VR128:$src2),
1430                      !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1431                      [(set VR128:$dst, (F64Int VR128:$src1, VR128:$src2))]>;
1432
1433   // Intrinsic operation, reg+mem.
1434   def SDrm_Int : SDI<opc, MRMSrcMem, (outs VR128:$dst),
1435                                      (ins VR128:$src1, sdmem:$src2),
1436                      !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1437                      [(set VR128:$dst, (F64Int VR128:$src1,
1438                                                sse_load_f64:$src2))]>;
1439 }
1440 }
1441
1442 // Arithmetic instructions
1443 defm ADD : basic_sse2_fp_binop_rm<0x58, "add", fadd, int_x86_sse2_add_sd, 1>;
1444 defm MUL : basic_sse2_fp_binop_rm<0x59, "mul", fmul, int_x86_sse2_mul_sd, 1>;
1445 defm SUB : basic_sse2_fp_binop_rm<0x5C, "sub", fsub, int_x86_sse2_sub_sd>;
1446 defm DIV : basic_sse2_fp_binop_rm<0x5E, "div", fdiv, int_x86_sse2_div_sd>;
1447
1448 /// sse2_fp_binop_rm - Other SSE2 binops
1449 ///
1450 /// This multiclass is like basic_sse2_fp_binop_rm, with the addition of
1451 /// instructions for a full-vector intrinsic form.  Operations that map
1452 /// onto C operators don't use this form since they just use the plain
1453 /// vector form instead of having a separate vector intrinsic form.
1454 ///
1455 /// This provides a total of eight "instructions".
1456 ///
1457 let Constraints = "$src1 = $dst" in {
1458 multiclass sse2_fp_binop_rm<bits<8> opc, string OpcodeStr,
1459                             SDNode OpNode,
1460                             Intrinsic F64Int,
1461                             Intrinsic V2F64Int,
1462                             bit Commutable = 0> {
1463
1464   // Scalar operation, reg+reg.
1465   def SDrr : SDI<opc, MRMSrcReg, (outs FR64:$dst), (ins FR64:$src1, FR64:$src2),
1466                  !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1467                  [(set FR64:$dst, (OpNode FR64:$src1, FR64:$src2))]> {
1468     let isCommutable = Commutable;
1469   }
1470
1471   // Scalar operation, reg+mem.
1472   def SDrm : SDI<opc, MRMSrcMem, (outs FR64:$dst),
1473                                  (ins FR64:$src1, f64mem:$src2),
1474                  !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1475                  [(set FR64:$dst, (OpNode FR64:$src1, (load addr:$src2)))]>;
1476
1477   // Vector operation, reg+reg.
1478   def PDrr : PDI<opc, MRMSrcReg, (outs VR128:$dst),
1479                                  (ins VR128:$src1, VR128:$src2),
1480                !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1481                [(set VR128:$dst, (v2f64 (OpNode VR128:$src1, VR128:$src2)))]> {
1482     let isCommutable = Commutable;
1483   }
1484
1485   // Vector operation, reg+mem.
1486   def PDrm : PDI<opc, MRMSrcMem, (outs VR128:$dst),
1487                                  (ins VR128:$src1, f128mem:$src2),
1488                  !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1489              [(set VR128:$dst, (OpNode VR128:$src1, (memopv2f64 addr:$src2)))]>;
1490
1491   // Intrinsic operation, reg+reg.
1492   def SDrr_Int : SDI<opc, MRMSrcReg, (outs VR128:$dst),
1493                                      (ins VR128:$src1, VR128:$src2),
1494                      !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1495                      [(set VR128:$dst, (F64Int VR128:$src1, VR128:$src2))]> {
1496     let isCommutable = Commutable;
1497   }
1498
1499   // Intrinsic operation, reg+mem.
1500   def SDrm_Int : SDI<opc, MRMSrcMem, (outs VR128:$dst),
1501                                      (ins VR128:$src1, sdmem:$src2),
1502                      !strconcat(OpcodeStr, "sd\t{$src2, $dst|$dst, $src2}"),
1503                      [(set VR128:$dst, (F64Int VR128:$src1,
1504                                                sse_load_f64:$src2))]>;
1505
1506   // Vector intrinsic operation, reg+reg.
1507   def PDrr_Int : PDI<opc, MRMSrcReg, (outs VR128:$dst),
1508                                      (ins VR128:$src1, VR128:$src2),
1509                      !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1510                      [(set VR128:$dst, (V2F64Int VR128:$src1, VR128:$src2))]> {
1511     let isCommutable = Commutable;
1512   }
1513
1514   // Vector intrinsic operation, reg+mem.
1515   def PDrm_Int : PDI<opc, MRMSrcMem, (outs VR128:$dst),
1516                                      (ins VR128:$src1, f128mem:$src2),
1517                      !strconcat(OpcodeStr, "pd\t{$src2, $dst|$dst, $src2}"),
1518                      [(set VR128:$dst, (V2F64Int VR128:$src1,
1519                                                  (memopv2f64 addr:$src2)))]>;
1520 }
1521 }
1522
1523 defm MAX : sse2_fp_binop_rm<0x5F, "max", X86fmax,
1524                             int_x86_sse2_max_sd, int_x86_sse2_max_pd>;
1525 defm MIN : sse2_fp_binop_rm<0x5D, "min", X86fmin,
1526                             int_x86_sse2_min_sd, int_x86_sse2_min_pd>;
1527
1528 //===---------------------------------------------------------------------===//
1529 // SSE packed FP Instructions
1530
1531 // Move Instructions
1532 let neverHasSideEffects = 1 in
1533 def MOVAPDrr : PDI<0x28, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1534                    "movapd\t{$src, $dst|$dst, $src}", []>;
1535 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in
1536 def MOVAPDrm : PDI<0x28, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1537                    "movapd\t{$src, $dst|$dst, $src}",
1538                    [(set VR128:$dst, (alignedloadv2f64 addr:$src))]>;
1539
1540 def MOVAPDmr : PDI<0x29, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
1541                    "movapd\t{$src, $dst|$dst, $src}",
1542                    [(alignedstore (v2f64 VR128:$src), addr:$dst)]>;
1543
1544 let neverHasSideEffects = 1 in
1545 def MOVUPDrr : PDI<0x10, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1546                    "movupd\t{$src, $dst|$dst, $src}", []>;
1547 let canFoldAsLoad = 1 in
1548 def MOVUPDrm : PDI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1549                    "movupd\t{$src, $dst|$dst, $src}",
1550                    [(set VR128:$dst, (loadv2f64 addr:$src))]>;
1551 def MOVUPDmr : PDI<0x11, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
1552                    "movupd\t{$src, $dst|$dst, $src}",
1553                    [(store (v2f64 VR128:$src), addr:$dst)]>;
1554
1555 // Intrinsic forms of MOVUPD load and store
1556 def MOVUPDrm_Int : PDI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1557                        "movupd\t{$src, $dst|$dst, $src}",
1558                        [(set VR128:$dst, (int_x86_sse2_loadu_pd addr:$src))]>;
1559 def MOVUPDmr_Int : PDI<0x11, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
1560                        "movupd\t{$src, $dst|$dst, $src}",
1561                        [(int_x86_sse2_storeu_pd addr:$dst, VR128:$src)]>;
1562
1563 let Constraints = "$src1 = $dst" in {
1564   let AddedComplexity = 20 in {
1565     def MOVLPDrm : PDI<0x12, MRMSrcMem,
1566                        (outs VR128:$dst), (ins VR128:$src1, f64mem:$src2),
1567                        "movlpd\t{$src2, $dst|$dst, $src2}",
1568                        [(set VR128:$dst,
1569                          (v2f64 (movlp VR128:$src1,
1570                                  (scalar_to_vector (loadf64 addr:$src2)))))]>;
1571     def MOVHPDrm : PDI<0x16, MRMSrcMem,
1572                        (outs VR128:$dst), (ins VR128:$src1, f64mem:$src2),
1573                        "movhpd\t{$src2, $dst|$dst, $src2}",
1574                        [(set VR128:$dst,
1575                          (v2f64 (movlhps VR128:$src1,
1576                                  (scalar_to_vector (loadf64 addr:$src2)))))]>;
1577   } // AddedComplexity
1578 } // Constraints = "$src1 = $dst"
1579
1580 def MOVLPDmr : PDI<0x13, MRMDestMem, (outs), (ins f64mem:$dst, VR128:$src),
1581                    "movlpd\t{$src, $dst|$dst, $src}",
1582                    [(store (f64 (vector_extract (v2f64 VR128:$src),
1583                                  (iPTR 0))), addr:$dst)]>;
1584
1585 // v2f64 extract element 1 is always custom lowered to unpack high to low
1586 // and extract element 0 so the non-store version isn't too horrible.
1587 def MOVHPDmr : PDI<0x17, MRMDestMem, (outs), (ins f64mem:$dst, VR128:$src),
1588                    "movhpd\t{$src, $dst|$dst, $src}",
1589                    [(store (f64 (vector_extract
1590                                  (v2f64 (unpckh VR128:$src, (undef))),
1591                                  (iPTR 0))), addr:$dst)]>;
1592
1593 // SSE2 instructions without OpSize prefix
1594 def Int_CVTDQ2PSrr : I<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1595                        "cvtdq2ps\t{$src, $dst|$dst, $src}",
1596                        [(set VR128:$dst, (int_x86_sse2_cvtdq2ps VR128:$src))]>,
1597                      TB, Requires<[HasSSE2]>;
1598 def Int_CVTDQ2PSrm : I<0x5B, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
1599                       "cvtdq2ps\t{$src, $dst|$dst, $src}",
1600                       [(set VR128:$dst, (int_x86_sse2_cvtdq2ps
1601                                         (bitconvert (memopv2i64 addr:$src))))]>,
1602                      TB, Requires<[HasSSE2]>;
1603
1604 // SSE2 instructions with XS prefix
1605 def Int_CVTDQ2PDrr : I<0xE6, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1606                        "cvtdq2pd\t{$src, $dst|$dst, $src}",
1607                        [(set VR128:$dst, (int_x86_sse2_cvtdq2pd VR128:$src))]>,
1608                      XS, Requires<[HasSSE2]>;
1609 def Int_CVTDQ2PDrm : I<0xE6, MRMSrcMem, (outs VR128:$dst), (ins i64mem:$src),
1610                      "cvtdq2pd\t{$src, $dst|$dst, $src}",
1611                      [(set VR128:$dst, (int_x86_sse2_cvtdq2pd
1612                                         (bitconvert (memopv2i64 addr:$src))))]>,
1613                      XS, Requires<[HasSSE2]>;
1614
1615 def Int_CVTPS2DQrr : PDI<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1616                         "cvtps2dq\t{$src, $dst|$dst, $src}",
1617                         [(set VR128:$dst, (int_x86_sse2_cvtps2dq VR128:$src))]>;
1618 def Int_CVTPS2DQrm : PDI<0x5B, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1619                          "cvtps2dq\t{$src, $dst|$dst, $src}",
1620                          [(set VR128:$dst, (int_x86_sse2_cvtps2dq
1621                                             (memop addr:$src)))]>;
1622 // SSE2 packed instructions with XS prefix
1623 def CVTTPS2DQrr : SSI<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1624                       "cvttps2dq\t{$src, $dst|$dst, $src}", []>;
1625 def CVTTPS2DQrm : SSI<0x5B, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1626                       "cvttps2dq\t{$src, $dst|$dst, $src}", []>;
1627
1628 def Int_CVTTPS2DQrr : I<0x5B, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1629                         "cvttps2dq\t{$src, $dst|$dst, $src}",
1630                         [(set VR128:$dst, 
1631                               (int_x86_sse2_cvttps2dq VR128:$src))]>,
1632                       XS, Requires<[HasSSE2]>;
1633 def Int_CVTTPS2DQrm : I<0x5B, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1634                         "cvttps2dq\t{$src, $dst|$dst, $src}",
1635                         [(set VR128:$dst, (int_x86_sse2_cvttps2dq
1636                                            (memop addr:$src)))]>,
1637                       XS, Requires<[HasSSE2]>;
1638
1639 // SSE2 packed instructions with XD prefix
1640 def Int_CVTPD2DQrr : I<0xE6, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1641                        "cvtpd2dq\t{$src, $dst|$dst, $src}",
1642                        [(set VR128:$dst, (int_x86_sse2_cvtpd2dq VR128:$src))]>,
1643                      XD, Requires<[HasSSE2]>;
1644 def Int_CVTPD2DQrm : I<0xE6, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1645                        "cvtpd2dq\t{$src, $dst|$dst, $src}",
1646                        [(set VR128:$dst, (int_x86_sse2_cvtpd2dq
1647                                           (memop addr:$src)))]>,
1648                      XD, Requires<[HasSSE2]>;
1649
1650 def Int_CVTTPD2DQrr : PDI<0xE6, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1651                           "cvttpd2dq\t{$src, $dst|$dst, $src}",
1652                        [(set VR128:$dst, (int_x86_sse2_cvttpd2dq VR128:$src))]>;
1653 def Int_CVTTPD2DQrm : PDI<0xE6, MRMSrcMem, (outs VR128:$dst),(ins f128mem:$src),
1654                           "cvttpd2dq\t{$src, $dst|$dst, $src}",
1655                           [(set VR128:$dst, (int_x86_sse2_cvttpd2dq
1656                                              (memop addr:$src)))]>;
1657
1658 // SSE2 instructions without OpSize prefix
1659 def CVTPS2PDrr : I<0x5A, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1660                        "cvtps2pd\t{$src, $dst|$dst, $src}", []>, TB;
1661 def CVTPS2PDrm : I<0x5A, MRMSrcMem, (outs VR128:$dst), (ins f64mem:$src),
1662                        "cvtps2pd\t{$src, $dst|$dst, $src}", []>, TB;
1663
1664 def Int_CVTPS2PDrr : I<0x5A, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1665                        "cvtps2pd\t{$src, $dst|$dst, $src}",
1666                        [(set VR128:$dst, (int_x86_sse2_cvtps2pd VR128:$src))]>,
1667                      TB, Requires<[HasSSE2]>;
1668 def Int_CVTPS2PDrm : I<0x5A, MRMSrcMem, (outs VR128:$dst), (ins f64mem:$src),
1669                        "cvtps2pd\t{$src, $dst|$dst, $src}",
1670                        [(set VR128:$dst, (int_x86_sse2_cvtps2pd
1671                                           (load addr:$src)))]>,
1672                      TB, Requires<[HasSSE2]>;
1673
1674 def CVTPD2PSrr : PDI<0x5A, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1675                      "cvtpd2ps\t{$src, $dst|$dst, $src}", []>;
1676 def CVTPD2PSrm : PDI<0x5A, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1677                      "cvtpd2ps\t{$src, $dst|$dst, $src}", []>;
1678
1679
1680 def Int_CVTPD2PSrr : PDI<0x5A, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1681                          "cvtpd2ps\t{$src, $dst|$dst, $src}",
1682                         [(set VR128:$dst, (int_x86_sse2_cvtpd2ps VR128:$src))]>;
1683 def Int_CVTPD2PSrm : PDI<0x5A, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1684                          "cvtpd2ps\t{$src, $dst|$dst, $src}",
1685                          [(set VR128:$dst, (int_x86_sse2_cvtpd2ps
1686                                             (memop addr:$src)))]>;
1687
1688 // Match intrinsics which expect XMM operand(s).
1689 // Aliases for intrinsics
1690 let Constraints = "$src1 = $dst" in {
1691 def Int_CVTSI2SDrr: SDI<0x2A, MRMSrcReg,
1692                         (outs VR128:$dst), (ins VR128:$src1, GR32:$src2),
1693                         "cvtsi2sd\t{$src2, $dst|$dst, $src2}",
1694                         [(set VR128:$dst, (int_x86_sse2_cvtsi2sd VR128:$src1,
1695                                            GR32:$src2))]>;
1696 def Int_CVTSI2SDrm: SDI<0x2A, MRMSrcMem,
1697                         (outs VR128:$dst), (ins VR128:$src1, i32mem:$src2),
1698                         "cvtsi2sd\t{$src2, $dst|$dst, $src2}",
1699                         [(set VR128:$dst, (int_x86_sse2_cvtsi2sd VR128:$src1,
1700                                            (loadi32 addr:$src2)))]>;
1701 def Int_CVTSD2SSrr: SDI<0x5A, MRMSrcReg,
1702                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1703                    "cvtsd2ss\t{$src2, $dst|$dst, $src2}",
1704                    [(set VR128:$dst, (int_x86_sse2_cvtsd2ss VR128:$src1,
1705                                       VR128:$src2))]>;
1706 def Int_CVTSD2SSrm: SDI<0x5A, MRMSrcMem,
1707                         (outs VR128:$dst), (ins VR128:$src1, f64mem:$src2),
1708                    "cvtsd2ss\t{$src2, $dst|$dst, $src2}",
1709                    [(set VR128:$dst, (int_x86_sse2_cvtsd2ss VR128:$src1,
1710                                       (load addr:$src2)))]>;
1711 def Int_CVTSS2SDrr: I<0x5A, MRMSrcReg,
1712                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1713                     "cvtss2sd\t{$src2, $dst|$dst, $src2}",
1714                     [(set VR128:$dst, (int_x86_sse2_cvtss2sd VR128:$src1,
1715                                        VR128:$src2))]>, XS,
1716                     Requires<[HasSSE2]>;
1717 def Int_CVTSS2SDrm: I<0x5A, MRMSrcMem,
1718                       (outs VR128:$dst), (ins VR128:$src1, f32mem:$src2),
1719                     "cvtss2sd\t{$src2, $dst|$dst, $src2}",
1720                     [(set VR128:$dst, (int_x86_sse2_cvtss2sd VR128:$src1,
1721                                        (load addr:$src2)))]>, XS,
1722                     Requires<[HasSSE2]>;
1723 }
1724
1725 // Arithmetic
1726
1727 /// sse2_fp_unop_rm - SSE2 unops come in both scalar and vector forms.
1728 ///
1729 /// In addition, we also have a special variant of the scalar form here to
1730 /// represent the associated intrinsic operation.  This form is unlike the
1731 /// plain scalar form, in that it takes an entire vector (instead of a
1732 /// scalar) and leaves the top elements undefined.
1733 ///
1734 /// And, we have a special variant form for a full-vector intrinsic form.
1735 ///
1736 /// These four forms can each have a reg or a mem operand, so there are a
1737 /// total of eight "instructions".
1738 ///
1739 multiclass sse2_fp_unop_rm<bits<8> opc, string OpcodeStr,
1740                            SDNode OpNode,
1741                            Intrinsic F64Int,
1742                            Intrinsic V2F64Int,
1743                            bit Commutable = 0> {
1744   // Scalar operation, reg.
1745   def SDr : SDI<opc, MRMSrcReg, (outs FR64:$dst), (ins FR64:$src),
1746                 !strconcat(OpcodeStr, "sd\t{$src, $dst|$dst, $src}"),
1747                 [(set FR64:$dst, (OpNode FR64:$src))]> {
1748     let isCommutable = Commutable;
1749   }
1750
1751   // Scalar operation, mem.
1752   def SDm : SDI<opc, MRMSrcMem, (outs FR64:$dst), (ins f64mem:$src),
1753                 !strconcat(OpcodeStr, "sd\t{$src, $dst|$dst, $src}"),
1754                 [(set FR64:$dst, (OpNode (load addr:$src)))]>;
1755
1756   // Vector operation, reg.
1757   def PDr : PDI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1758               !strconcat(OpcodeStr, "pd\t{$src, $dst|$dst, $src}"),
1759               [(set VR128:$dst, (v2f64 (OpNode VR128:$src)))]> {
1760     let isCommutable = Commutable;
1761   }
1762
1763   // Vector operation, mem.
1764   def PDm : PDI<opc, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1765                 !strconcat(OpcodeStr, "pd\t{$src, $dst|$dst, $src}"),
1766                 [(set VR128:$dst, (OpNode (memopv2f64 addr:$src)))]>;
1767
1768   // Intrinsic operation, reg.
1769   def SDr_Int : SDI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1770                     !strconcat(OpcodeStr, "sd\t{$src, $dst|$dst, $src}"),
1771                     [(set VR128:$dst, (F64Int VR128:$src))]> {
1772     let isCommutable = Commutable;
1773   }
1774
1775   // Intrinsic operation, mem.
1776   def SDm_Int : SDI<opc, MRMSrcMem, (outs VR128:$dst), (ins sdmem:$src),
1777                     !strconcat(OpcodeStr, "sd\t{$src, $dst|$dst, $src}"),
1778                     [(set VR128:$dst, (F64Int sse_load_f64:$src))]>;
1779
1780   // Vector intrinsic operation, reg
1781   def PDr_Int : PDI<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1782                     !strconcat(OpcodeStr, "pd\t{$src, $dst|$dst, $src}"),
1783                     [(set VR128:$dst, (V2F64Int VR128:$src))]> {
1784     let isCommutable = Commutable;
1785   }
1786
1787   // Vector intrinsic operation, mem
1788   def PDm_Int : PDI<opc, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
1789                     !strconcat(OpcodeStr, "pd\t{$src, $dst|$dst, $src}"),
1790                     [(set VR128:$dst, (V2F64Int (memopv2f64 addr:$src)))]>;
1791 }
1792
1793 // Square root.
1794 defm SQRT  : sse2_fp_unop_rm<0x51, "sqrt",  fsqrt,
1795                              int_x86_sse2_sqrt_sd, int_x86_sse2_sqrt_pd>;
1796
1797 // There is no f64 version of the reciprocal approximation instructions.
1798
1799 // Logical
1800 let Constraints = "$src1 = $dst" in {
1801   let isCommutable = 1 in {
1802     def ANDPDrr : PDI<0x54, MRMSrcReg,
1803                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1804                       "andpd\t{$src2, $dst|$dst, $src2}",
1805                       [(set VR128:$dst,
1806                         (and (bc_v2i64 (v2f64 VR128:$src1)),
1807                          (bc_v2i64 (v2f64 VR128:$src2))))]>;
1808     def ORPDrr  : PDI<0x56, MRMSrcReg,
1809                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1810                       "orpd\t{$src2, $dst|$dst, $src2}",
1811                       [(set VR128:$dst,
1812                         (or (bc_v2i64 (v2f64 VR128:$src1)),
1813                          (bc_v2i64 (v2f64 VR128:$src2))))]>;
1814     def XORPDrr : PDI<0x57, MRMSrcReg,
1815                       (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1816                       "xorpd\t{$src2, $dst|$dst, $src2}",
1817                       [(set VR128:$dst,
1818                         (xor (bc_v2i64 (v2f64 VR128:$src1)),
1819                          (bc_v2i64 (v2f64 VR128:$src2))))]>;
1820   }
1821
1822   def ANDPDrm : PDI<0x54, MRMSrcMem,
1823                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1824                     "andpd\t{$src2, $dst|$dst, $src2}",
1825                     [(set VR128:$dst,
1826                       (and (bc_v2i64 (v2f64 VR128:$src1)),
1827                        (memopv2i64 addr:$src2)))]>;
1828   def ORPDrm  : PDI<0x56, MRMSrcMem,
1829                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1830                     "orpd\t{$src2, $dst|$dst, $src2}",
1831                     [(set VR128:$dst,
1832                       (or (bc_v2i64 (v2f64 VR128:$src1)),
1833                        (memopv2i64 addr:$src2)))]>;
1834   def XORPDrm : PDI<0x57, MRMSrcMem,
1835                     (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1836                     "xorpd\t{$src2, $dst|$dst, $src2}",
1837                     [(set VR128:$dst,
1838                       (xor (bc_v2i64 (v2f64 VR128:$src1)),
1839                        (memopv2i64 addr:$src2)))]>;
1840   def ANDNPDrr : PDI<0x55, MRMSrcReg,
1841                      (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1842                      "andnpd\t{$src2, $dst|$dst, $src2}",
1843                      [(set VR128:$dst,
1844                        (and (vnot (bc_v2i64 (v2f64 VR128:$src1))),
1845                         (bc_v2i64 (v2f64 VR128:$src2))))]>;
1846   def ANDNPDrm : PDI<0x55, MRMSrcMem,
1847                      (outs VR128:$dst), (ins VR128:$src1,f128mem:$src2),
1848                      "andnpd\t{$src2, $dst|$dst, $src2}",
1849                      [(set VR128:$dst,
1850                        (and (vnot (bc_v2i64 (v2f64 VR128:$src1))),
1851                         (memopv2i64 addr:$src2)))]>;
1852 }
1853
1854 let Constraints = "$src1 = $dst" in {
1855   def CMPPDrri : PDIi8<0xC2, MRMSrcReg,
1856                     (outs VR128:$dst), (ins VR128:$src1, VR128:$src, SSECC:$cc),
1857                     "cmp${cc}pd\t{$src, $dst|$dst, $src}",
1858                     [(set VR128:$dst, (int_x86_sse2_cmp_pd VR128:$src1,
1859                                                         VR128:$src, imm:$cc))]>;
1860   def CMPPDrmi : PDIi8<0xC2, MRMSrcMem,
1861                   (outs VR128:$dst), (ins VR128:$src1, f128mem:$src, SSECC:$cc),
1862                   "cmp${cc}pd\t{$src, $dst|$dst, $src}",
1863                   [(set VR128:$dst, (int_x86_sse2_cmp_pd VR128:$src1,
1864                                                  (memop addr:$src), imm:$cc))]>;
1865 }
1866 def : Pat<(v2i64 (X86cmppd (v2f64 VR128:$src1), VR128:$src2, imm:$cc)),
1867           (CMPPDrri VR128:$src1, VR128:$src2, imm:$cc)>;
1868 def : Pat<(v2i64 (X86cmppd (v2f64 VR128:$src1), (memop addr:$src2), imm:$cc)),
1869           (CMPPDrmi VR128:$src1, addr:$src2, imm:$cc)>;
1870
1871 // Shuffle and unpack instructions
1872 let Constraints = "$src1 = $dst" in {
1873   def SHUFPDrri : PDIi8<0xC6, MRMSrcReg,
1874                  (outs VR128:$dst), (ins VR128:$src1, VR128:$src2, i8imm:$src3),
1875                  "shufpd\t{$src3, $src2, $dst|$dst, $src2, $src3}",
1876                  [(set VR128:$dst,
1877                    (v2f64 (shufp:$src3 VR128:$src1, VR128:$src2)))]>;
1878   def SHUFPDrmi : PDIi8<0xC6, MRMSrcMem,
1879                         (outs VR128:$dst), (ins VR128:$src1,
1880                          f128mem:$src2, i8imm:$src3),
1881                         "shufpd\t{$src3, $src2, $dst|$dst, $src2, $src3}",
1882                         [(set VR128:$dst,
1883                           (v2f64 (shufp:$src3
1884                                   VR128:$src1, (memopv2f64 addr:$src2))))]>;
1885
1886   let AddedComplexity = 10 in {
1887     def UNPCKHPDrr : PDI<0x15, MRMSrcReg,
1888                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1889                          "unpckhpd\t{$src2, $dst|$dst, $src2}",
1890                          [(set VR128:$dst,
1891                            (v2f64 (unpckh VR128:$src1, VR128:$src2)))]>;
1892     def UNPCKHPDrm : PDI<0x15, MRMSrcMem,
1893                          (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1894                          "unpckhpd\t{$src2, $dst|$dst, $src2}",
1895                          [(set VR128:$dst,
1896                            (v2f64 (unpckh VR128:$src1,
1897                                           (memopv2f64 addr:$src2))))]>;
1898
1899     def UNPCKLPDrr : PDI<0x14, MRMSrcReg,
1900                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
1901                          "unpcklpd\t{$src2, $dst|$dst, $src2}",
1902                          [(set VR128:$dst,
1903                            (v2f64 (unpckl VR128:$src1, VR128:$src2)))]>;
1904     def UNPCKLPDrm : PDI<0x14, MRMSrcMem,
1905                          (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
1906                          "unpcklpd\t{$src2, $dst|$dst, $src2}",
1907                          [(set VR128:$dst,
1908                            (unpckl VR128:$src1, (memopv2f64 addr:$src2)))]>;
1909   } // AddedComplexity
1910 } // Constraints = "$src1 = $dst"
1911
1912
1913 //===---------------------------------------------------------------------===//
1914 // SSE integer instructions
1915
1916 // Move Instructions
1917 let neverHasSideEffects = 1 in
1918 def MOVDQArr : PDI<0x6F, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
1919                    "movdqa\t{$src, $dst|$dst, $src}", []>;
1920 let canFoldAsLoad = 1, mayLoad = 1 in
1921 def MOVDQArm : PDI<0x6F, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
1922                    "movdqa\t{$src, $dst|$dst, $src}",
1923                    [/*(set VR128:$dst, (alignedloadv2i64 addr:$src))*/]>;
1924 let mayStore = 1 in
1925 def MOVDQAmr : PDI<0x7F, MRMDestMem, (outs), (ins i128mem:$dst, VR128:$src),
1926                    "movdqa\t{$src, $dst|$dst, $src}",
1927                    [/*(alignedstore (v2i64 VR128:$src), addr:$dst)*/]>;
1928 let canFoldAsLoad = 1, mayLoad = 1 in
1929 def MOVDQUrm :   I<0x6F, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
1930                    "movdqu\t{$src, $dst|$dst, $src}",
1931                    [/*(set VR128:$dst, (loadv2i64 addr:$src))*/]>,
1932                  XS, Requires<[HasSSE2]>;
1933 let mayStore = 1 in
1934 def MOVDQUmr :   I<0x7F, MRMDestMem, (outs), (ins i128mem:$dst, VR128:$src),
1935                    "movdqu\t{$src, $dst|$dst, $src}",
1936                    [/*(store (v2i64 VR128:$src), addr:$dst)*/]>,
1937                  XS, Requires<[HasSSE2]>;
1938
1939 // Intrinsic forms of MOVDQU load and store
1940 let canFoldAsLoad = 1 in
1941 def MOVDQUrm_Int :   I<0x6F, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
1942                        "movdqu\t{$src, $dst|$dst, $src}",
1943                        [(set VR128:$dst, (int_x86_sse2_loadu_dq addr:$src))]>,
1944                  XS, Requires<[HasSSE2]>;
1945 def MOVDQUmr_Int :   I<0x7F, MRMDestMem, (outs), (ins i128mem:$dst, VR128:$src),
1946                        "movdqu\t{$src, $dst|$dst, $src}",
1947                        [(int_x86_sse2_storeu_dq addr:$dst, VR128:$src)]>,
1948                      XS, Requires<[HasSSE2]>;
1949
1950 let Constraints = "$src1 = $dst" in {
1951
1952 multiclass PDI_binop_rm_int<bits<8> opc, string OpcodeStr, Intrinsic IntId,
1953                             bit Commutable = 0> {
1954   def rr : PDI<opc, MRMSrcReg, (outs VR128:$dst), 
1955                                (ins VR128:$src1, VR128:$src2),
1956                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1957                [(set VR128:$dst, (IntId VR128:$src1, VR128:$src2))]> {
1958     let isCommutable = Commutable;
1959   }
1960   def rm : PDI<opc, MRMSrcMem, (outs VR128:$dst), 
1961                                (ins VR128:$src1, i128mem:$src2),
1962                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1963                [(set VR128:$dst, (IntId VR128:$src1,
1964                                         (bitconvert (memopv2i64 
1965                                                      addr:$src2))))]>;
1966 }
1967
1968 multiclass PDI_binop_rmi_int<bits<8> opc, bits<8> opc2, Format ImmForm,
1969                              string OpcodeStr,
1970                              Intrinsic IntId, Intrinsic IntId2> {
1971   def rr : PDI<opc, MRMSrcReg, (outs VR128:$dst), 
1972                                (ins VR128:$src1, VR128:$src2),
1973                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1974                [(set VR128:$dst, (IntId VR128:$src1, VR128:$src2))]>;
1975   def rm : PDI<opc, MRMSrcMem, (outs VR128:$dst),
1976                                (ins VR128:$src1, i128mem:$src2),
1977                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1978                [(set VR128:$dst, (IntId VR128:$src1,
1979                                       (bitconvert (memopv2i64 addr:$src2))))]>;
1980   def ri : PDIi8<opc2, ImmForm, (outs VR128:$dst), 
1981                                 (ins VR128:$src1, i32i8imm:$src2),
1982                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1983                [(set VR128:$dst, (IntId2 VR128:$src1, (i32 imm:$src2)))]>;
1984 }
1985
1986 /// PDI_binop_rm - Simple SSE2 binary operator.
1987 multiclass PDI_binop_rm<bits<8> opc, string OpcodeStr, SDNode OpNode,
1988                         ValueType OpVT, bit Commutable = 0> {
1989   def rr : PDI<opc, MRMSrcReg, (outs VR128:$dst), 
1990                                (ins VR128:$src1, VR128:$src2),
1991                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1992                [(set VR128:$dst, (OpVT (OpNode VR128:$src1, VR128:$src2)))]> {
1993     let isCommutable = Commutable;
1994   }
1995   def rm : PDI<opc, MRMSrcMem, (outs VR128:$dst), 
1996                                (ins VR128:$src1, i128mem:$src2),
1997                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
1998                [(set VR128:$dst, (OpVT (OpNode VR128:$src1,
1999                                      (bitconvert (memopv2i64 addr:$src2)))))]>;
2000 }
2001
2002 /// PDI_binop_rm_v2i64 - Simple SSE2 binary operator whose type is v2i64.
2003 ///
2004 /// FIXME: we could eliminate this and use PDI_binop_rm instead if tblgen knew
2005 /// to collapse (bitconvert VT to VT) into its operand.
2006 ///
2007 multiclass PDI_binop_rm_v2i64<bits<8> opc, string OpcodeStr, SDNode OpNode,
2008                               bit Commutable = 0> {
2009   def rr : PDI<opc, MRMSrcReg, (outs VR128:$dst),
2010                (ins VR128:$src1, VR128:$src2),
2011                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2012                [(set VR128:$dst, (v2i64 (OpNode VR128:$src1, VR128:$src2)))]> {
2013     let isCommutable = Commutable;
2014   }
2015   def rm : PDI<opc, MRMSrcMem, (outs VR128:$dst),
2016                (ins VR128:$src1, i128mem:$src2),
2017                !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2018                [(set VR128:$dst, (OpNode VR128:$src1,
2019                (memopv2i64 addr:$src2)))]>;
2020 }
2021
2022 } // Constraints = "$src1 = $dst"
2023
2024 // 128-bit Integer Arithmetic
2025
2026 defm PADDB : PDI_binop_rm<0xFC, "paddb", add, v16i8, 1>;
2027 defm PADDW : PDI_binop_rm<0xFD, "paddw", add, v8i16, 1>;
2028 defm PADDD : PDI_binop_rm<0xFE, "paddd", add, v4i32, 1>;
2029 defm PADDQ : PDI_binop_rm_v2i64<0xD4, "paddq", add, 1>;
2030
2031 defm PADDSB  : PDI_binop_rm_int<0xEC, "paddsb" , int_x86_sse2_padds_b, 1>;
2032 defm PADDSW  : PDI_binop_rm_int<0xED, "paddsw" , int_x86_sse2_padds_w, 1>;
2033 defm PADDUSB : PDI_binop_rm_int<0xDC, "paddusb", int_x86_sse2_paddus_b, 1>;
2034 defm PADDUSW : PDI_binop_rm_int<0xDD, "paddusw", int_x86_sse2_paddus_w, 1>;
2035
2036 defm PSUBB : PDI_binop_rm<0xF8, "psubb", sub, v16i8>;
2037 defm PSUBW : PDI_binop_rm<0xF9, "psubw", sub, v8i16>;
2038 defm PSUBD : PDI_binop_rm<0xFA, "psubd", sub, v4i32>;
2039 defm PSUBQ : PDI_binop_rm_v2i64<0xFB, "psubq", sub>;
2040
2041 defm PSUBSB  : PDI_binop_rm_int<0xE8, "psubsb" , int_x86_sse2_psubs_b>;
2042 defm PSUBSW  : PDI_binop_rm_int<0xE9, "psubsw" , int_x86_sse2_psubs_w>;
2043 defm PSUBUSB : PDI_binop_rm_int<0xD8, "psubusb", int_x86_sse2_psubus_b>;
2044 defm PSUBUSW : PDI_binop_rm_int<0xD9, "psubusw", int_x86_sse2_psubus_w>;
2045
2046 defm PMULLW : PDI_binop_rm<0xD5, "pmullw", mul, v8i16, 1>;
2047
2048 defm PMULHUW : PDI_binop_rm_int<0xE4, "pmulhuw", int_x86_sse2_pmulhu_w, 1>;
2049 defm PMULHW  : PDI_binop_rm_int<0xE5, "pmulhw" , int_x86_sse2_pmulh_w , 1>;
2050 defm PMULUDQ : PDI_binop_rm_int<0xF4, "pmuludq", int_x86_sse2_pmulu_dq, 1>;
2051
2052 defm PMADDWD : PDI_binop_rm_int<0xF5, "pmaddwd", int_x86_sse2_pmadd_wd, 1>;
2053
2054 defm PAVGB  : PDI_binop_rm_int<0xE0, "pavgb", int_x86_sse2_pavg_b, 1>;
2055 defm PAVGW  : PDI_binop_rm_int<0xE3, "pavgw", int_x86_sse2_pavg_w, 1>;
2056
2057
2058 defm PMINUB : PDI_binop_rm_int<0xDA, "pminub", int_x86_sse2_pminu_b, 1>;
2059 defm PMINSW : PDI_binop_rm_int<0xEA, "pminsw", int_x86_sse2_pmins_w, 1>;
2060 defm PMAXUB : PDI_binop_rm_int<0xDE, "pmaxub", int_x86_sse2_pmaxu_b, 1>;
2061 defm PMAXSW : PDI_binop_rm_int<0xEE, "pmaxsw", int_x86_sse2_pmaxs_w, 1>;
2062 defm PSADBW : PDI_binop_rm_int<0xF6, "psadbw", int_x86_sse2_psad_bw, 1>;
2063
2064
2065 defm PSLLW : PDI_binop_rmi_int<0xF1, 0x71, MRM6r, "psllw",
2066                                int_x86_sse2_psll_w, int_x86_sse2_pslli_w>;
2067 defm PSLLD : PDI_binop_rmi_int<0xF2, 0x72, MRM6r, "pslld",
2068                                int_x86_sse2_psll_d, int_x86_sse2_pslli_d>;
2069 defm PSLLQ : PDI_binop_rmi_int<0xF3, 0x73, MRM6r, "psllq",
2070                                int_x86_sse2_psll_q, int_x86_sse2_pslli_q>;
2071
2072 defm PSRLW : PDI_binop_rmi_int<0xD1, 0x71, MRM2r, "psrlw",
2073                                int_x86_sse2_psrl_w, int_x86_sse2_psrli_w>;
2074 defm PSRLD : PDI_binop_rmi_int<0xD2, 0x72, MRM2r, "psrld",
2075                                int_x86_sse2_psrl_d, int_x86_sse2_psrli_d>;
2076 defm PSRLQ : PDI_binop_rmi_int<0xD3, 0x73, MRM2r, "psrlq",
2077                                int_x86_sse2_psrl_q, int_x86_sse2_psrli_q>;
2078
2079 defm PSRAW : PDI_binop_rmi_int<0xE1, 0x71, MRM4r, "psraw",
2080                                int_x86_sse2_psra_w, int_x86_sse2_psrai_w>;
2081 defm PSRAD : PDI_binop_rmi_int<0xE2, 0x72, MRM4r, "psrad",
2082                                int_x86_sse2_psra_d, int_x86_sse2_psrai_d>;
2083
2084 // 128-bit logical shifts.
2085 let Constraints = "$src1 = $dst", neverHasSideEffects = 1 in {
2086   def PSLLDQri : PDIi8<0x73, MRM7r,
2087                        (outs VR128:$dst), (ins VR128:$src1, i32i8imm:$src2),
2088                        "pslldq\t{$src2, $dst|$dst, $src2}", []>;
2089   def PSRLDQri : PDIi8<0x73, MRM3r,
2090                        (outs VR128:$dst), (ins VR128:$src1, i32i8imm:$src2),
2091                        "psrldq\t{$src2, $dst|$dst, $src2}", []>;
2092   // PSRADQri doesn't exist in SSE[1-3].
2093 }
2094
2095 let Predicates = [HasSSE2] in {
2096   def : Pat<(int_x86_sse2_psll_dq VR128:$src1, imm:$src2),
2097             (v2i64 (PSLLDQri VR128:$src1, (BYTE_imm imm:$src2)))>;
2098   def : Pat<(int_x86_sse2_psrl_dq VR128:$src1, imm:$src2),
2099             (v2i64 (PSRLDQri VR128:$src1, (BYTE_imm imm:$src2)))>;
2100   def : Pat<(int_x86_sse2_psll_dq_bs VR128:$src1, imm:$src2),
2101             (v2i64 (PSLLDQri VR128:$src1, imm:$src2))>;
2102   def : Pat<(int_x86_sse2_psrl_dq_bs VR128:$src1, imm:$src2),
2103             (v2i64 (PSRLDQri VR128:$src1, imm:$src2))>;
2104   def : Pat<(v2f64 (X86fsrl VR128:$src1, i32immSExt8:$src2)),
2105             (v2f64 (PSRLDQri VR128:$src1, (BYTE_imm imm:$src2)))>;
2106
2107   // Shift up / down and insert zero's.
2108   def : Pat<(v2i64 (X86vshl  VR128:$src, (i8 imm:$amt))),
2109             (v2i64 (PSLLDQri VR128:$src, (BYTE_imm imm:$amt)))>;
2110   def : Pat<(v2i64 (X86vshr  VR128:$src, (i8 imm:$amt))),
2111             (v2i64 (PSRLDQri VR128:$src, (BYTE_imm imm:$amt)))>;
2112 }
2113
2114 // Logical
2115 defm PAND : PDI_binop_rm_v2i64<0xDB, "pand", and, 1>;
2116 defm POR  : PDI_binop_rm_v2i64<0xEB, "por" , or , 1>;
2117 defm PXOR : PDI_binop_rm_v2i64<0xEF, "pxor", xor, 1>;
2118
2119 let Constraints = "$src1 = $dst" in {
2120   def PANDNrr : PDI<0xDF, MRMSrcReg,
2121                     (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2122                     "pandn\t{$src2, $dst|$dst, $src2}",
2123                     [(set VR128:$dst, (v2i64 (and (vnot VR128:$src1),
2124                                               VR128:$src2)))]>;
2125
2126   def PANDNrm : PDI<0xDF, MRMSrcMem,
2127                     (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2128                     "pandn\t{$src2, $dst|$dst, $src2}",
2129                     [(set VR128:$dst, (v2i64 (and (vnot VR128:$src1),
2130                                               (memopv2i64 addr:$src2))))]>;
2131 }
2132
2133 // SSE2 Integer comparison
2134 defm PCMPEQB  : PDI_binop_rm_int<0x74, "pcmpeqb", int_x86_sse2_pcmpeq_b>;
2135 defm PCMPEQW  : PDI_binop_rm_int<0x75, "pcmpeqw", int_x86_sse2_pcmpeq_w>;
2136 defm PCMPEQD  : PDI_binop_rm_int<0x76, "pcmpeqd", int_x86_sse2_pcmpeq_d>;
2137 defm PCMPGTB  : PDI_binop_rm_int<0x64, "pcmpgtb", int_x86_sse2_pcmpgt_b>;
2138 defm PCMPGTW  : PDI_binop_rm_int<0x65, "pcmpgtw", int_x86_sse2_pcmpgt_w>;
2139 defm PCMPGTD  : PDI_binop_rm_int<0x66, "pcmpgtd", int_x86_sse2_pcmpgt_d>;
2140
2141 def : Pat<(v16i8 (X86pcmpeqb VR128:$src1, VR128:$src2)),
2142           (PCMPEQBrr VR128:$src1, VR128:$src2)>;
2143 def : Pat<(v16i8 (X86pcmpeqb VR128:$src1, (memop addr:$src2))),
2144           (PCMPEQBrm VR128:$src1, addr:$src2)>;
2145 def : Pat<(v8i16 (X86pcmpeqw VR128:$src1, VR128:$src2)),
2146           (PCMPEQWrr VR128:$src1, VR128:$src2)>;
2147 def : Pat<(v8i16 (X86pcmpeqw VR128:$src1, (memop addr:$src2))),
2148           (PCMPEQWrm VR128:$src1, addr:$src2)>;
2149 def : Pat<(v4i32 (X86pcmpeqd VR128:$src1, VR128:$src2)),
2150           (PCMPEQDrr VR128:$src1, VR128:$src2)>;
2151 def : Pat<(v4i32 (X86pcmpeqd VR128:$src1, (memop addr:$src2))),
2152           (PCMPEQDrm VR128:$src1, addr:$src2)>;
2153
2154 def : Pat<(v16i8 (X86pcmpgtb VR128:$src1, VR128:$src2)),
2155           (PCMPGTBrr VR128:$src1, VR128:$src2)>;
2156 def : Pat<(v16i8 (X86pcmpgtb VR128:$src1, (memop addr:$src2))),
2157           (PCMPGTBrm VR128:$src1, addr:$src2)>;
2158 def : Pat<(v8i16 (X86pcmpgtw VR128:$src1, VR128:$src2)),
2159           (PCMPGTWrr VR128:$src1, VR128:$src2)>;
2160 def : Pat<(v8i16 (X86pcmpgtw VR128:$src1, (memop addr:$src2))),
2161           (PCMPGTWrm VR128:$src1, addr:$src2)>;
2162 def : Pat<(v4i32 (X86pcmpgtd VR128:$src1, VR128:$src2)),
2163           (PCMPGTDrr VR128:$src1, VR128:$src2)>;
2164 def : Pat<(v4i32 (X86pcmpgtd VR128:$src1, (memop addr:$src2))),
2165           (PCMPGTDrm VR128:$src1, addr:$src2)>;
2166
2167
2168 // Pack instructions
2169 defm PACKSSWB : PDI_binop_rm_int<0x63, "packsswb", int_x86_sse2_packsswb_128>;
2170 defm PACKSSDW : PDI_binop_rm_int<0x6B, "packssdw", int_x86_sse2_packssdw_128>;
2171 defm PACKUSWB : PDI_binop_rm_int<0x67, "packuswb", int_x86_sse2_packuswb_128>;
2172
2173 // Shuffle and unpack instructions
2174 let AddedComplexity = 5 in {
2175 def PSHUFDri : PDIi8<0x70, MRMSrcReg,
2176                      (outs VR128:$dst), (ins VR128:$src1, i8imm:$src2),
2177                      "pshufd\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2178                      [(set VR128:$dst, (v4i32 (pshufd:$src2
2179                                                VR128:$src1, (undef))))]>;
2180 def PSHUFDmi : PDIi8<0x70, MRMSrcMem,
2181                      (outs VR128:$dst), (ins i128mem:$src1, i8imm:$src2),
2182                      "pshufd\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2183                      [(set VR128:$dst, (v4i32 (pshufd:$src2
2184                                              (bc_v4i32 (memopv2i64 addr:$src1)),
2185                                              (undef))))]>;
2186 }
2187
2188 // SSE2 with ImmT == Imm8 and XS prefix.
2189 def PSHUFHWri : Ii8<0x70, MRMSrcReg,
2190                     (outs VR128:$dst), (ins VR128:$src1, i8imm:$src2),
2191                     "pshufhw\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2192                     [(set VR128:$dst, (v8i16 (pshufhw:$src2 VR128:$src1,
2193                                                             (undef))))]>,
2194                 XS, Requires<[HasSSE2]>;
2195 def PSHUFHWmi : Ii8<0x70, MRMSrcMem,
2196                     (outs VR128:$dst), (ins i128mem:$src1, i8imm:$src2),
2197                     "pshufhw\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2198                     [(set VR128:$dst, (v8i16 (pshufhw:$src2
2199                                             (bc_v8i16 (memopv2i64 addr:$src1)),
2200                                             (undef))))]>,
2201                 XS, Requires<[HasSSE2]>;
2202
2203 // SSE2 with ImmT == Imm8 and XD prefix.
2204 def PSHUFLWri : Ii8<0x70, MRMSrcReg,
2205                     (outs VR128:$dst), (ins VR128:$src1, i8imm:$src2),
2206                     "pshuflw\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2207                     [(set VR128:$dst, (v8i16 (pshuflw:$src2 VR128:$src1,
2208                                                             (undef))))]>,
2209                 XD, Requires<[HasSSE2]>;
2210 def PSHUFLWmi : Ii8<0x70, MRMSrcMem,
2211                     (outs VR128:$dst), (ins i128mem:$src1, i8imm:$src2),
2212                     "pshuflw\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2213                     [(set VR128:$dst, (v8i16 (pshuflw:$src2
2214                                              (bc_v8i16 (memopv2i64 addr:$src1)),
2215                                              (undef))))]>,
2216                 XD, Requires<[HasSSE2]>;
2217
2218
2219 let Constraints = "$src1 = $dst" in {
2220   def PUNPCKLBWrr : PDI<0x60, MRMSrcReg,
2221                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2222                         "punpcklbw\t{$src2, $dst|$dst, $src2}",
2223                         [(set VR128:$dst,
2224                           (v16i8 (unpckl VR128:$src1, VR128:$src2)))]>;
2225   def PUNPCKLBWrm : PDI<0x60, MRMSrcMem,
2226                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2227                         "punpcklbw\t{$src2, $dst|$dst, $src2}",
2228                         [(set VR128:$dst,
2229                           (unpckl VR128:$src1,
2230                                   (bc_v16i8 (memopv2i64 addr:$src2))))]>;
2231   def PUNPCKLWDrr : PDI<0x61, MRMSrcReg,
2232                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2233                         "punpcklwd\t{$src2, $dst|$dst, $src2}",
2234                         [(set VR128:$dst,
2235                           (v8i16 (unpckl VR128:$src1, VR128:$src2)))]>;
2236   def PUNPCKLWDrm : PDI<0x61, MRMSrcMem,
2237                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2238                         "punpcklwd\t{$src2, $dst|$dst, $src2}",
2239                         [(set VR128:$dst,
2240                           (unpckl VR128:$src1,
2241                                   (bc_v8i16 (memopv2i64 addr:$src2))))]>;
2242   def PUNPCKLDQrr : PDI<0x62, MRMSrcReg,
2243                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2244                         "punpckldq\t{$src2, $dst|$dst, $src2}",
2245                         [(set VR128:$dst,
2246                           (v4i32 (unpckl VR128:$src1, VR128:$src2)))]>;
2247   def PUNPCKLDQrm : PDI<0x62, MRMSrcMem,
2248                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2249                         "punpckldq\t{$src2, $dst|$dst, $src2}",
2250                         [(set VR128:$dst,
2251                           (unpckl VR128:$src1,
2252                                   (bc_v4i32 (memopv2i64 addr:$src2))))]>;
2253   def PUNPCKLQDQrr : PDI<0x6C, MRMSrcReg,
2254                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2255                          "punpcklqdq\t{$src2, $dst|$dst, $src2}",
2256                         [(set VR128:$dst,
2257                           (v2i64 (unpckl VR128:$src1, VR128:$src2)))]>;
2258   def PUNPCKLQDQrm : PDI<0x6C, MRMSrcMem,
2259                          (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2260                          "punpcklqdq\t{$src2, $dst|$dst, $src2}",
2261                         [(set VR128:$dst,
2262                           (v2i64 (unpckl VR128:$src1,
2263                                          (memopv2i64 addr:$src2))))]>;
2264
2265   def PUNPCKHBWrr : PDI<0x68, MRMSrcReg,
2266                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2267                         "punpckhbw\t{$src2, $dst|$dst, $src2}",
2268                         [(set VR128:$dst,
2269                           (v16i8 (unpckh VR128:$src1, VR128:$src2)))]>;
2270   def PUNPCKHBWrm : PDI<0x68, MRMSrcMem,
2271                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2272                         "punpckhbw\t{$src2, $dst|$dst, $src2}",
2273                         [(set VR128:$dst,
2274                           (unpckh VR128:$src1,
2275                                   (bc_v16i8 (memopv2i64 addr:$src2))))]>;
2276   def PUNPCKHWDrr : PDI<0x69, MRMSrcReg,
2277                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2278                         "punpckhwd\t{$src2, $dst|$dst, $src2}",
2279                         [(set VR128:$dst,
2280                           (v8i16 (unpckh VR128:$src1, VR128:$src2)))]>;
2281   def PUNPCKHWDrm : PDI<0x69, MRMSrcMem,
2282                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2283                         "punpckhwd\t{$src2, $dst|$dst, $src2}",
2284                         [(set VR128:$dst,
2285                           (unpckh VR128:$src1,
2286                                   (bc_v8i16 (memopv2i64 addr:$src2))))]>;
2287   def PUNPCKHDQrr : PDI<0x6A, MRMSrcReg,
2288                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2289                         "punpckhdq\t{$src2, $dst|$dst, $src2}",
2290                         [(set VR128:$dst,
2291                           (v4i32 (unpckh VR128:$src1, VR128:$src2)))]>;
2292   def PUNPCKHDQrm : PDI<0x6A, MRMSrcMem,
2293                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2294                         "punpckhdq\t{$src2, $dst|$dst, $src2}",
2295                         [(set VR128:$dst,
2296                           (unpckh VR128:$src1,
2297                                   (bc_v4i32 (memopv2i64 addr:$src2))))]>;
2298   def PUNPCKHQDQrr : PDI<0x6D, MRMSrcReg,
2299                          (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2300                          "punpckhqdq\t{$src2, $dst|$dst, $src2}",
2301                         [(set VR128:$dst,
2302                           (v2i64 (unpckh VR128:$src1, VR128:$src2)))]>;
2303   def PUNPCKHQDQrm : PDI<0x6D, MRMSrcMem,
2304                         (outs VR128:$dst), (ins VR128:$src1, i128mem:$src2),
2305                         "punpckhqdq\t{$src2, $dst|$dst, $src2}",
2306                         [(set VR128:$dst,
2307                           (v2i64 (unpckh VR128:$src1,
2308                                          (memopv2i64 addr:$src2))))]>;
2309 }
2310
2311 // Extract / Insert
2312 def PEXTRWri : PDIi8<0xC5, MRMSrcReg,
2313                     (outs GR32:$dst), (ins VR128:$src1, i32i8imm:$src2),
2314                     "pextrw\t{$src2, $src1, $dst|$dst, $src1, $src2}",
2315                     [(set GR32:$dst, (X86pextrw (v8i16 VR128:$src1),
2316                                                 imm:$src2))]>;
2317 let Constraints = "$src1 = $dst" in {
2318   def PINSRWrri : PDIi8<0xC4, MRMSrcReg,
2319                        (outs VR128:$dst), (ins VR128:$src1,
2320                         GR32:$src2, i32i8imm:$src3),
2321                        "pinsrw\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2322                        [(set VR128:$dst,
2323                          (X86pinsrw VR128:$src1, GR32:$src2, imm:$src3))]>;
2324   def PINSRWrmi : PDIi8<0xC4, MRMSrcMem,
2325                        (outs VR128:$dst), (ins VR128:$src1,
2326                         i16mem:$src2, i32i8imm:$src3),
2327                        "pinsrw\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2328                        [(set VR128:$dst,
2329                          (X86pinsrw VR128:$src1, (extloadi16 addr:$src2),
2330                                     imm:$src3))]>;
2331 }
2332
2333 // Mask creation
2334 def PMOVMSKBrr : PDI<0xD7, MRMSrcReg, (outs GR32:$dst), (ins VR128:$src),
2335                      "pmovmskb\t{$src, $dst|$dst, $src}",
2336                      [(set GR32:$dst, (int_x86_sse2_pmovmskb_128 VR128:$src))]>;
2337
2338 // Conditional store
2339 let Uses = [EDI] in
2340 def MASKMOVDQU : PDI<0xF7, MRMSrcReg, (outs), (ins VR128:$src, VR128:$mask),
2341                      "maskmovdqu\t{$mask, $src|$src, $mask}",
2342                      [(int_x86_sse2_maskmov_dqu VR128:$src, VR128:$mask, EDI)]>;
2343
2344 let Uses = [RDI] in
2345 def MASKMOVDQU64 : PDI<0xF7, MRMSrcReg, (outs), (ins VR128:$src, VR128:$mask),
2346                      "maskmovdqu\t{$mask, $src|$src, $mask}",
2347                      [(int_x86_sse2_maskmov_dqu VR128:$src, VR128:$mask, RDI)]>;
2348
2349 // Non-temporal stores
2350 def MOVNTPDmr_Int : PDI<0x2B, MRMDestMem, (outs), (ins i128mem:$dst, VR128:$src),
2351                         "movntpd\t{$src, $dst|$dst, $src}",
2352                         [(int_x86_sse2_movnt_pd addr:$dst, VR128:$src)]>;
2353 def MOVNTDQmr_Int : PDI<0xE7, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
2354                         "movntdq\t{$src, $dst|$dst, $src}",
2355                         [(int_x86_sse2_movnt_dq addr:$dst, VR128:$src)]>;
2356 def MOVNTImr_Int  :   I<0xC3, MRMDestMem, (outs), (ins i32mem:$dst, GR32:$src),
2357                     "movnti\t{$src, $dst|$dst, $src}",
2358                     [(int_x86_sse2_movnt_i addr:$dst, GR32:$src)]>,
2359                   TB, Requires<[HasSSE2]>;
2360
2361 let AddedComplexity = 400 in { // Prefer non-temporal versions
2362 def MOVNTPDmr : PDI<0x2B, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
2363                     "movntpd\t{$src, $dst|$dst, $src}",
2364                     [(alignednontemporalstore(v2f64 VR128:$src), addr:$dst)]>;
2365
2366 def MOVNTDQmr : PDI<0xE7, MRMDestMem, (outs), (ins f128mem:$dst, VR128:$src),
2367                     "movntdq\t{$src, $dst|$dst, $src}",
2368                     [(alignednontemporalstore (v4f32 VR128:$src), addr:$dst)]>;
2369
2370 def : Pat<(alignednontemporalstore (v4i32 VR128:$src), addr:$dst),
2371           (MOVNTDQmr VR128:$src, addr:$dst)>;
2372 }
2373
2374 // Flush cache
2375 def CLFLUSH : I<0xAE, MRM7m, (outs), (ins i8mem:$src),
2376                "clflush\t$src", [(int_x86_sse2_clflush addr:$src)]>,
2377               TB, Requires<[HasSSE2]>;
2378
2379 // Load, store, and memory fence
2380 def LFENCE : I<0xAE, MRM_E8, (outs), (ins),
2381                "lfence", [(int_x86_sse2_lfence)]>, TB, Requires<[HasSSE2]>;
2382 def MFENCE : I<0xAE, MRM_F0, (outs), (ins),
2383                "mfence", [(int_x86_sse2_mfence)]>, TB, Requires<[HasSSE2]>;
2384
2385 //TODO: custom lower this so as to never even generate the noop
2386 def : Pat<(membarrier (i8 imm:$ll), (i8 imm:$ls), (i8 imm:$sl), (i8 imm:$ss),
2387            (i8 0)), (NOOP)>;
2388 def : Pat<(membarrier (i8 0), (i8 0), (i8 0), (i8 1), (i8 1)), (SFENCE)>;
2389 def : Pat<(membarrier (i8 1), (i8 0), (i8 0), (i8 0), (i8 1)), (LFENCE)>;
2390 def : Pat<(membarrier (i8 imm:$ll), (i8 imm:$ls), (i8 imm:$sl), (i8 imm:$ss),
2391            (i8 1)), (MFENCE)>;
2392
2393 // Alias instructions that map zero vector to pxor / xorp* for sse.
2394 // We set canFoldAsLoad because this can be converted to a constant-pool
2395 // load of an all-ones value if folding it would be beneficial.
2396 let isReMaterializable = 1, isAsCheapAsAMove = 1, canFoldAsLoad = 1,
2397     isCodeGenOnly = 1 in
2398   // FIXME: Change encoding to pseudo.
2399   def V_SETALLONES : PDI<0x76, MRMInitReg, (outs VR128:$dst), (ins), "",
2400                          [(set VR128:$dst, (v4i32 immAllOnesV))]>;
2401
2402 // FR64 to 128-bit vector conversion.
2403 let isAsCheapAsAMove = 1 in
2404 def MOVSD2PDrr : SDI<0x10, MRMSrcReg, (outs VR128:$dst), (ins FR64:$src),
2405                       "movsd\t{$src, $dst|$dst, $src}",
2406                       [(set VR128:$dst,
2407                         (v2f64 (scalar_to_vector FR64:$src)))]>;
2408 def MOVSD2PDrm : SDI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f64mem:$src),
2409                      "movsd\t{$src, $dst|$dst, $src}",
2410                      [(set VR128:$dst,
2411                        (v2f64 (scalar_to_vector (loadf64 addr:$src))))]>;
2412
2413 def MOVDI2PDIrr : PDI<0x6E, MRMSrcReg, (outs VR128:$dst), (ins GR32:$src),
2414                       "movd\t{$src, $dst|$dst, $src}",
2415                       [(set VR128:$dst,
2416                         (v4i32 (scalar_to_vector GR32:$src)))]>;
2417 def MOVDI2PDIrm : PDI<0x6E, MRMSrcMem, (outs VR128:$dst), (ins i32mem:$src),
2418                       "movd\t{$src, $dst|$dst, $src}",
2419                       [(set VR128:$dst,
2420                         (v4i32 (scalar_to_vector (loadi32 addr:$src))))]>;
2421
2422 def MOVDI2SSrr  : PDI<0x6E, MRMSrcReg, (outs FR32:$dst), (ins GR32:$src),
2423                       "movd\t{$src, $dst|$dst, $src}",
2424                       [(set FR32:$dst, (bitconvert GR32:$src))]>;
2425
2426 def MOVDI2SSrm  : PDI<0x6E, MRMSrcMem, (outs FR32:$dst), (ins i32mem:$src),
2427                       "movd\t{$src, $dst|$dst, $src}",
2428                       [(set FR32:$dst, (bitconvert (loadi32 addr:$src)))]>;
2429
2430 // SSE2 instructions with XS prefix
2431 def MOVQI2PQIrm : I<0x7E, MRMSrcMem, (outs VR128:$dst), (ins i64mem:$src),
2432                     "movq\t{$src, $dst|$dst, $src}",
2433                     [(set VR128:$dst,
2434                       (v2i64 (scalar_to_vector (loadi64 addr:$src))))]>, XS,
2435                   Requires<[HasSSE2]>;
2436 def MOVPQI2QImr : PDI<0xD6, MRMDestMem, (outs), (ins i64mem:$dst, VR128:$src),
2437                       "movq\t{$src, $dst|$dst, $src}",
2438                       [(store (i64 (vector_extract (v2i64 VR128:$src),
2439                                     (iPTR 0))), addr:$dst)]>;
2440
2441 // FIXME: may not be able to eliminate this movss with coalescing the src and
2442 // dest register classes are different. We really want to write this pattern
2443 // like this:
2444 // def : Pat<(f32 (vector_extract (v4f32 VR128:$src), (iPTR 0))),
2445 //           (f32 FR32:$src)>;
2446 let isAsCheapAsAMove = 1 in
2447 def MOVPD2SDrr : SDI<0x10, MRMSrcReg, (outs FR64:$dst), (ins VR128:$src),
2448                      "movsd\t{$src, $dst|$dst, $src}",
2449                      [(set FR64:$dst, (vector_extract (v2f64 VR128:$src),
2450                                        (iPTR 0)))]>;
2451 def MOVPD2SDmr : SDI<0x11, MRMDestMem, (outs), (ins f64mem:$dst, VR128:$src),
2452                      "movsd\t{$src, $dst|$dst, $src}",
2453                      [(store (f64 (vector_extract (v2f64 VR128:$src),
2454                                    (iPTR 0))), addr:$dst)]>;
2455 def MOVPDI2DIrr  : PDI<0x7E, MRMDestReg, (outs GR32:$dst), (ins VR128:$src),
2456                        "movd\t{$src, $dst|$dst, $src}",
2457                        [(set GR32:$dst, (vector_extract (v4i32 VR128:$src),
2458                                         (iPTR 0)))]>;
2459 def MOVPDI2DImr  : PDI<0x7E, MRMDestMem, (outs), (ins i32mem:$dst, VR128:$src),
2460                        "movd\t{$src, $dst|$dst, $src}",
2461                        [(store (i32 (vector_extract (v4i32 VR128:$src),
2462                                      (iPTR 0))), addr:$dst)]>;
2463
2464 def MOVSS2DIrr  : PDI<0x7E, MRMDestReg, (outs GR32:$dst), (ins FR32:$src),
2465                       "movd\t{$src, $dst|$dst, $src}",
2466                       [(set GR32:$dst, (bitconvert FR32:$src))]>;
2467 def MOVSS2DImr  : PDI<0x7E, MRMDestMem, (outs), (ins i32mem:$dst, FR32:$src),
2468                       "movd\t{$src, $dst|$dst, $src}",
2469                       [(store (i32 (bitconvert FR32:$src)), addr:$dst)]>;
2470
2471
2472 // Move to lower bits of a VR128, leaving upper bits alone.
2473 // Three operand (but two address) aliases.
2474 let Constraints = "$src1 = $dst" in {
2475   let neverHasSideEffects = 1 in
2476   def MOVLSD2PDrr : SDI<0x10, MRMSrcReg,
2477                         (outs VR128:$dst), (ins VR128:$src1, FR64:$src2),
2478                         "movsd\t{$src2, $dst|$dst, $src2}", []>;
2479
2480   let AddedComplexity = 15 in
2481     def MOVLPDrr : SDI<0x10, MRMSrcReg,
2482                        (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2483                        "movsd\t{$src2, $dst|$dst, $src2}",
2484                        [(set VR128:$dst,
2485                          (v2f64 (movl VR128:$src1, VR128:$src2)))]>;
2486 }
2487
2488 // Store / copy lower 64-bits of a XMM register.
2489 def MOVLQ128mr : PDI<0xD6, MRMDestMem, (outs), (ins i64mem:$dst, VR128:$src),
2490                      "movq\t{$src, $dst|$dst, $src}",
2491                      [(int_x86_sse2_storel_dq addr:$dst, VR128:$src)]>;
2492
2493 // Move to lower bits of a VR128 and zeroing upper bits.
2494 // Loading from memory automatically zeroing upper bits.
2495 let AddedComplexity = 20 in {
2496 def MOVZSD2PDrm : SDI<0x10, MRMSrcMem, (outs VR128:$dst), (ins f64mem:$src),
2497                       "movsd\t{$src, $dst|$dst, $src}",
2498                       [(set VR128:$dst,
2499                         (v2f64 (X86vzmovl (v2f64 (scalar_to_vector
2500                                                  (loadf64 addr:$src))))))]>;
2501
2502 def : Pat<(v2f64 (X86vzmovl (loadv2f64 addr:$src))),
2503             (MOVZSD2PDrm addr:$src)>;
2504 def : Pat<(v2f64 (X86vzmovl (bc_v2f64 (loadv4f32 addr:$src)))),
2505             (MOVZSD2PDrm addr:$src)>;
2506 def : Pat<(v2f64 (X86vzload addr:$src)), (MOVZSD2PDrm addr:$src)>;
2507 }
2508
2509 // movd / movq to XMM register zero-extends
2510 let AddedComplexity = 15 in {
2511 def MOVZDI2PDIrr : PDI<0x6E, MRMSrcReg, (outs VR128:$dst), (ins GR32:$src),
2512                        "movd\t{$src, $dst|$dst, $src}",
2513                        [(set VR128:$dst, (v4i32 (X86vzmovl
2514                                       (v4i32 (scalar_to_vector GR32:$src)))))]>;
2515 // This is X86-64 only.
2516 def MOVZQI2PQIrr : RPDI<0x6E, MRMSrcReg, (outs VR128:$dst), (ins GR64:$src),
2517                        "mov{d|q}\t{$src, $dst|$dst, $src}",
2518                        [(set VR128:$dst, (v2i64 (X86vzmovl
2519                                       (v2i64 (scalar_to_vector GR64:$src)))))]>;
2520 }
2521
2522 let AddedComplexity = 20 in {
2523 def MOVZDI2PDIrm : PDI<0x6E, MRMSrcMem, (outs VR128:$dst), (ins i32mem:$src),
2524                        "movd\t{$src, $dst|$dst, $src}",
2525                        [(set VR128:$dst,
2526                          (v4i32 (X86vzmovl (v4i32 (scalar_to_vector
2527                                                    (loadi32 addr:$src))))))]>;
2528
2529 def : Pat<(v4i32 (X86vzmovl (loadv4i32 addr:$src))),
2530             (MOVZDI2PDIrm addr:$src)>;
2531 def : Pat<(v4i32 (X86vzmovl (bc_v4i32 (loadv4f32 addr:$src)))),
2532             (MOVZDI2PDIrm addr:$src)>;
2533 def : Pat<(v4i32 (X86vzmovl (bc_v4i32 (loadv2i64 addr:$src)))),
2534             (MOVZDI2PDIrm addr:$src)>;
2535
2536 def MOVZQI2PQIrm : I<0x7E, MRMSrcMem, (outs VR128:$dst), (ins i64mem:$src),
2537                      "movq\t{$src, $dst|$dst, $src}",
2538                      [(set VR128:$dst,
2539                        (v2i64 (X86vzmovl (v2i64 (scalar_to_vector
2540                                                  (loadi64 addr:$src))))))]>, XS,
2541                    Requires<[HasSSE2]>;
2542
2543 def : Pat<(v2i64 (X86vzmovl (loadv2i64 addr:$src))),
2544             (MOVZQI2PQIrm addr:$src)>;
2545 def : Pat<(v2i64 (X86vzmovl (bc_v2i64 (loadv4f32 addr:$src)))),
2546             (MOVZQI2PQIrm addr:$src)>;
2547 def : Pat<(v2i64 (X86vzload addr:$src)), (MOVZQI2PQIrm addr:$src)>;
2548 }
2549
2550 // Moving from XMM to XMM and clear upper 64 bits. Note, there is a bug in
2551 // IA32 document. movq xmm1, xmm2 does clear the high bits.
2552 let AddedComplexity = 15 in
2553 def MOVZPQILo2PQIrr : I<0x7E, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
2554                         "movq\t{$src, $dst|$dst, $src}",
2555                     [(set VR128:$dst, (v2i64 (X86vzmovl (v2i64 VR128:$src))))]>,
2556                       XS, Requires<[HasSSE2]>;
2557
2558 let AddedComplexity = 20 in {
2559 def MOVZPQILo2PQIrm : I<0x7E, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
2560                         "movq\t{$src, $dst|$dst, $src}",
2561                     [(set VR128:$dst, (v2i64 (X86vzmovl
2562                                              (loadv2i64 addr:$src))))]>,
2563                       XS, Requires<[HasSSE2]>;
2564
2565 def : Pat<(v2i64 (X86vzmovl (bc_v2i64 (loadv4i32 addr:$src)))),
2566             (MOVZPQILo2PQIrm addr:$src)>;
2567 }
2568
2569 // Instructions for the disassembler
2570 // xr = XMM register
2571 // xm = mem64
2572
2573 def MOVQxrxr : I<0x7E, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
2574                  "movq\t{$src, $dst|$dst, $src}", []>, XS;
2575
2576 //===---------------------------------------------------------------------===//
2577 // SSE3 Instructions
2578 //===---------------------------------------------------------------------===//
2579
2580 // Move Instructions
2581 def MOVSHDUPrr : S3SI<0x16, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
2582                       "movshdup\t{$src, $dst|$dst, $src}",
2583                       [(set VR128:$dst, (v4f32 (movshdup
2584                                                 VR128:$src, (undef))))]>;
2585 def MOVSHDUPrm : S3SI<0x16, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
2586                       "movshdup\t{$src, $dst|$dst, $src}",
2587                       [(set VR128:$dst, (movshdup
2588                                          (memopv4f32 addr:$src), (undef)))]>;
2589
2590 def MOVSLDUPrr : S3SI<0x12, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
2591                       "movsldup\t{$src, $dst|$dst, $src}",
2592                       [(set VR128:$dst, (v4f32 (movsldup
2593                                                 VR128:$src, (undef))))]>;
2594 def MOVSLDUPrm : S3SI<0x12, MRMSrcMem, (outs VR128:$dst), (ins f128mem:$src),
2595                       "movsldup\t{$src, $dst|$dst, $src}",
2596                       [(set VR128:$dst, (movsldup
2597                                          (memopv4f32 addr:$src), (undef)))]>;
2598
2599 def MOVDDUPrr  : S3DI<0x12, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
2600                       "movddup\t{$src, $dst|$dst, $src}",
2601                       [(set VR128:$dst,(v2f64 (movddup VR128:$src, (undef))))]>;
2602 def MOVDDUPrm  : S3DI<0x12, MRMSrcMem, (outs VR128:$dst), (ins f64mem:$src),
2603                       "movddup\t{$src, $dst|$dst, $src}",
2604                     [(set VR128:$dst,
2605                       (v2f64 (movddup (scalar_to_vector (loadf64 addr:$src)),
2606                                       (undef))))]>;
2607
2608 def : Pat<(movddup (bc_v2f64 (v2i64 (scalar_to_vector (loadi64 addr:$src)))),
2609                    (undef)),
2610           (MOVDDUPrm addr:$src)>, Requires<[HasSSE3]>;
2611
2612 let AddedComplexity = 5 in {
2613 def : Pat<(movddup (memopv2f64 addr:$src), (undef)),
2614           (MOVDDUPrm addr:$src)>, Requires<[HasSSE3]>;
2615 def : Pat<(movddup (bc_v4f32 (memopv2f64 addr:$src)), (undef)),
2616           (MOVDDUPrm addr:$src)>, Requires<[HasSSE3]>;
2617 def : Pat<(movddup (memopv2i64 addr:$src), (undef)),
2618           (MOVDDUPrm addr:$src)>, Requires<[HasSSE3]>;
2619 def : Pat<(movddup (bc_v4i32 (memopv2i64 addr:$src)), (undef)),
2620           (MOVDDUPrm addr:$src)>, Requires<[HasSSE3]>;
2621 }
2622
2623 // Arithmetic
2624 let Constraints = "$src1 = $dst" in {
2625   def ADDSUBPSrr : S3DI<0xD0, MRMSrcReg,
2626                         (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2627                         "addsubps\t{$src2, $dst|$dst, $src2}",
2628                         [(set VR128:$dst, (int_x86_sse3_addsub_ps VR128:$src1,
2629                                            VR128:$src2))]>;
2630   def ADDSUBPSrm : S3DI<0xD0, MRMSrcMem,
2631                         (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
2632                         "addsubps\t{$src2, $dst|$dst, $src2}",
2633                         [(set VR128:$dst, (int_x86_sse3_addsub_ps VR128:$src1,
2634                                            (memop addr:$src2)))]>;
2635   def ADDSUBPDrr : S3I<0xD0, MRMSrcReg,
2636                        (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2637                        "addsubpd\t{$src2, $dst|$dst, $src2}",
2638                        [(set VR128:$dst, (int_x86_sse3_addsub_pd VR128:$src1,
2639                                           VR128:$src2))]>;
2640   def ADDSUBPDrm : S3I<0xD0, MRMSrcMem,
2641                        (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
2642                        "addsubpd\t{$src2, $dst|$dst, $src2}",
2643                        [(set VR128:$dst, (int_x86_sse3_addsub_pd VR128:$src1,
2644                                           (memop addr:$src2)))]>;
2645 }
2646
2647 def LDDQUrm : S3DI<0xF0, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
2648                    "lddqu\t{$src, $dst|$dst, $src}",
2649                    [(set VR128:$dst, (int_x86_sse3_ldu_dq addr:$src))]>;
2650
2651 // Horizontal ops
2652 class S3D_Intrr<bits<8> o, string OpcodeStr, Intrinsic IntId>
2653   : S3DI<o, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2654          !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2655          [(set VR128:$dst, (v4f32 (IntId VR128:$src1, VR128:$src2)))]>;
2656 class S3D_Intrm<bits<8> o, string OpcodeStr, Intrinsic IntId>
2657   : S3DI<o, MRMSrcMem, (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
2658          !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2659          [(set VR128:$dst, (v4f32 (IntId VR128:$src1, (memop addr:$src2))))]>;
2660 class S3_Intrr<bits<8> o, string OpcodeStr, Intrinsic IntId>
2661   : S3I<o, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src1, VR128:$src2),
2662         !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2663         [(set VR128:$dst, (v2f64 (IntId VR128:$src1, VR128:$src2)))]>;
2664 class S3_Intrm<bits<8> o, string OpcodeStr, Intrinsic IntId>
2665   : S3I<o, MRMSrcMem, (outs VR128:$dst), (ins VR128:$src1, f128mem:$src2),
2666         !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2667       [(set VR128:$dst, (v2f64 (IntId VR128:$src1, (memopv2f64 addr:$src2))))]>;
2668
2669 let Constraints = "$src1 = $dst" in {
2670   def HADDPSrr : S3D_Intrr<0x7C, "haddps", int_x86_sse3_hadd_ps>;
2671   def HADDPSrm : S3D_Intrm<0x7C, "haddps", int_x86_sse3_hadd_ps>;
2672   def HADDPDrr : S3_Intrr <0x7C, "haddpd", int_x86_sse3_hadd_pd>;
2673   def HADDPDrm : S3_Intrm <0x7C, "haddpd", int_x86_sse3_hadd_pd>;
2674   def HSUBPSrr : S3D_Intrr<0x7D, "hsubps", int_x86_sse3_hsub_ps>;
2675   def HSUBPSrm : S3D_Intrm<0x7D, "hsubps", int_x86_sse3_hsub_ps>;
2676   def HSUBPDrr : S3_Intrr <0x7D, "hsubpd", int_x86_sse3_hsub_pd>;
2677   def HSUBPDrm : S3_Intrm <0x7D, "hsubpd", int_x86_sse3_hsub_pd>;
2678 }
2679
2680 // Thread synchronization
2681 def MONITOR : I<0x01, MRM_C8, (outs), (ins), "monitor",
2682                 [(int_x86_sse3_monitor EAX, ECX, EDX)]>,TB, Requires<[HasSSE3]>;
2683 def MWAIT   : I<0x01, MRM_C9, (outs), (ins), "mwait",
2684                 [(int_x86_sse3_mwait ECX, EAX)]>, TB, Requires<[HasSSE3]>;
2685
2686 // vector_shuffle v1, <undef> <1, 1, 3, 3>
2687 let AddedComplexity = 15 in
2688 def : Pat<(v4i32 (movshdup VR128:$src, (undef))),
2689           (MOVSHDUPrr VR128:$src)>, Requires<[HasSSE3]>;
2690 let AddedComplexity = 20 in
2691 def : Pat<(v4i32 (movshdup (bc_v4i32 (memopv2i64 addr:$src)), (undef))),
2692           (MOVSHDUPrm addr:$src)>, Requires<[HasSSE3]>;
2693
2694 // vector_shuffle v1, <undef> <0, 0, 2, 2>
2695 let AddedComplexity = 15 in
2696   def : Pat<(v4i32 (movsldup VR128:$src, (undef))),
2697             (MOVSLDUPrr VR128:$src)>, Requires<[HasSSE3]>;
2698 let AddedComplexity = 20 in
2699   def : Pat<(v4i32 (movsldup (bc_v4i32 (memopv2i64 addr:$src)), (undef))),
2700             (MOVSLDUPrm addr:$src)>, Requires<[HasSSE3]>;
2701
2702 //===---------------------------------------------------------------------===//
2703 // SSSE3 Instructions
2704 //===---------------------------------------------------------------------===//
2705
2706 /// SS3I_unop_rm_int_8 - Simple SSSE3 unary operator whose type is v*i8.
2707 multiclass SS3I_unop_rm_int_8<bits<8> opc, string OpcodeStr,
2708                               Intrinsic IntId64, Intrinsic IntId128> {
2709   def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst), (ins VR64:$src),
2710                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2711                    [(set VR64:$dst, (IntId64 VR64:$src))]>;
2712
2713   def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst), (ins i64mem:$src),
2714                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2715                    [(set VR64:$dst,
2716                      (IntId64 (bitconvert (memopv8i8 addr:$src))))]>;
2717
2718   def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2719                     (ins VR128:$src),
2720                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2721                     [(set VR128:$dst, (IntId128 VR128:$src))]>,
2722                     OpSize;
2723
2724   def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2725                     (ins i128mem:$src),
2726                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2727                     [(set VR128:$dst,
2728                       (IntId128
2729                        (bitconvert (memopv16i8 addr:$src))))]>, OpSize;
2730 }
2731
2732 /// SS3I_unop_rm_int_16 - Simple SSSE3 unary operator whose type is v*i16.
2733 multiclass SS3I_unop_rm_int_16<bits<8> opc, string OpcodeStr,
2734                                Intrinsic IntId64, Intrinsic IntId128> {
2735   def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst),
2736                    (ins VR64:$src),
2737                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2738                    [(set VR64:$dst, (IntId64 VR64:$src))]>;
2739
2740   def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst),
2741                    (ins i64mem:$src),
2742                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2743                    [(set VR64:$dst,
2744                      (IntId64
2745                       (bitconvert (memopv4i16 addr:$src))))]>;
2746
2747   def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2748                     (ins VR128:$src),
2749                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2750                     [(set VR128:$dst, (IntId128 VR128:$src))]>,
2751                     OpSize;
2752
2753   def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2754                     (ins i128mem:$src),
2755                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2756                     [(set VR128:$dst,
2757                       (IntId128
2758                        (bitconvert (memopv8i16 addr:$src))))]>, OpSize;
2759 }
2760
2761 /// SS3I_unop_rm_int_32 - Simple SSSE3 unary operator whose type is v*i32.
2762 multiclass SS3I_unop_rm_int_32<bits<8> opc, string OpcodeStr,
2763                                Intrinsic IntId64, Intrinsic IntId128> {
2764   def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst),
2765                    (ins VR64:$src),
2766                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2767                    [(set VR64:$dst, (IntId64 VR64:$src))]>;
2768
2769   def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst),
2770                    (ins i64mem:$src),
2771                    !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2772                    [(set VR64:$dst,
2773                      (IntId64
2774                       (bitconvert (memopv2i32 addr:$src))))]>;
2775
2776   def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2777                     (ins VR128:$src),
2778                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2779                     [(set VR128:$dst, (IntId128 VR128:$src))]>,
2780                     OpSize;
2781
2782   def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2783                     (ins i128mem:$src),
2784                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
2785                     [(set VR128:$dst,
2786                       (IntId128
2787                        (bitconvert (memopv4i32 addr:$src))))]>, OpSize;
2788 }
2789
2790 defm PABSB       : SS3I_unop_rm_int_8 <0x1C, "pabsb",
2791                                        int_x86_ssse3_pabs_b,
2792                                        int_x86_ssse3_pabs_b_128>;
2793 defm PABSW       : SS3I_unop_rm_int_16<0x1D, "pabsw",
2794                                        int_x86_ssse3_pabs_w,
2795                                        int_x86_ssse3_pabs_w_128>;
2796 defm PABSD       : SS3I_unop_rm_int_32<0x1E, "pabsd",
2797                                        int_x86_ssse3_pabs_d,
2798                                        int_x86_ssse3_pabs_d_128>;
2799
2800 /// SS3I_binop_rm_int_8 - Simple SSSE3 binary operator whose type is v*i8.
2801 let Constraints = "$src1 = $dst" in {
2802   multiclass SS3I_binop_rm_int_8<bits<8> opc, string OpcodeStr,
2803                                  Intrinsic IntId64, Intrinsic IntId128,
2804                                  bit Commutable = 0> {
2805     def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst),
2806                      (ins VR64:$src1, VR64:$src2),
2807                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2808                      [(set VR64:$dst, (IntId64 VR64:$src1, VR64:$src2))]> {
2809       let isCommutable = Commutable;
2810     }
2811     def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst),
2812                      (ins VR64:$src1, i64mem:$src2),
2813                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2814                      [(set VR64:$dst,
2815                        (IntId64 VR64:$src1,
2816                         (bitconvert (memopv8i8 addr:$src2))))]>;
2817
2818     def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2819                       (ins VR128:$src1, VR128:$src2),
2820                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2821                       [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
2822                       OpSize {
2823       let isCommutable = Commutable;
2824     }
2825     def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2826                       (ins VR128:$src1, i128mem:$src2),
2827                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2828                       [(set VR128:$dst,
2829                         (IntId128 VR128:$src1,
2830                          (bitconvert (memopv16i8 addr:$src2))))]>, OpSize;
2831   }
2832 }
2833
2834 /// SS3I_binop_rm_int_16 - Simple SSSE3 binary operator whose type is v*i16.
2835 let Constraints = "$src1 = $dst" in {
2836   multiclass SS3I_binop_rm_int_16<bits<8> opc, string OpcodeStr,
2837                                   Intrinsic IntId64, Intrinsic IntId128,
2838                                   bit Commutable = 0> {
2839     def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst),
2840                      (ins VR64:$src1, VR64:$src2),
2841                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2842                      [(set VR64:$dst, (IntId64 VR64:$src1, VR64:$src2))]> {
2843       let isCommutable = Commutable;
2844     }
2845     def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst),
2846                      (ins VR64:$src1, i64mem:$src2),
2847                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2848                      [(set VR64:$dst,
2849                        (IntId64 VR64:$src1,
2850                         (bitconvert (memopv4i16 addr:$src2))))]>;
2851
2852     def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2853                       (ins VR128:$src1, VR128:$src2),
2854                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2855                       [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
2856                       OpSize {
2857       let isCommutable = Commutable;
2858     }
2859     def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2860                       (ins VR128:$src1, i128mem:$src2),
2861                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2862                       [(set VR128:$dst,
2863                         (IntId128 VR128:$src1,
2864                          (bitconvert (memopv8i16 addr:$src2))))]>, OpSize;
2865   }
2866 }
2867
2868 /// SS3I_binop_rm_int_32 - Simple SSSE3 binary operator whose type is v*i32.
2869 let Constraints = "$src1 = $dst" in {
2870   multiclass SS3I_binop_rm_int_32<bits<8> opc, string OpcodeStr,
2871                                   Intrinsic IntId64, Intrinsic IntId128,
2872                                   bit Commutable = 0> {
2873     def rr64 : SS38I<opc, MRMSrcReg, (outs VR64:$dst),
2874                      (ins VR64:$src1, VR64:$src2),
2875                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2876                      [(set VR64:$dst, (IntId64 VR64:$src1, VR64:$src2))]> {
2877       let isCommutable = Commutable;
2878     }
2879     def rm64 : SS38I<opc, MRMSrcMem, (outs VR64:$dst),
2880                      (ins VR64:$src1, i64mem:$src2),
2881                      !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2882                      [(set VR64:$dst,
2883                        (IntId64 VR64:$src1,
2884                         (bitconvert (memopv2i32 addr:$src2))))]>;
2885
2886     def rr128 : SS38I<opc, MRMSrcReg, (outs VR128:$dst),
2887                       (ins VR128:$src1, VR128:$src2),
2888                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2889                       [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
2890                       OpSize {
2891       let isCommutable = Commutable;
2892     }
2893     def rm128 : SS38I<opc, MRMSrcMem, (outs VR128:$dst),
2894                       (ins VR128:$src1, i128mem:$src2),
2895                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
2896                       [(set VR128:$dst,
2897                         (IntId128 VR128:$src1,
2898                          (bitconvert (memopv4i32 addr:$src2))))]>, OpSize;
2899   }
2900 }
2901
2902 defm PHADDW      : SS3I_binop_rm_int_16<0x01, "phaddw",
2903                                         int_x86_ssse3_phadd_w,
2904                                         int_x86_ssse3_phadd_w_128>;
2905 defm PHADDD      : SS3I_binop_rm_int_32<0x02, "phaddd",
2906                                         int_x86_ssse3_phadd_d,
2907                                         int_x86_ssse3_phadd_d_128>;
2908 defm PHADDSW     : SS3I_binop_rm_int_16<0x03, "phaddsw",
2909                                         int_x86_ssse3_phadd_sw,
2910                                         int_x86_ssse3_phadd_sw_128>;
2911 defm PHSUBW      : SS3I_binop_rm_int_16<0x05, "phsubw",
2912                                         int_x86_ssse3_phsub_w,
2913                                         int_x86_ssse3_phsub_w_128>;
2914 defm PHSUBD      : SS3I_binop_rm_int_32<0x06, "phsubd",
2915                                         int_x86_ssse3_phsub_d,
2916                                         int_x86_ssse3_phsub_d_128>;
2917 defm PHSUBSW     : SS3I_binop_rm_int_16<0x07, "phsubsw",
2918                                         int_x86_ssse3_phsub_sw,
2919                                         int_x86_ssse3_phsub_sw_128>;
2920 defm PMADDUBSW   : SS3I_binop_rm_int_8 <0x04, "pmaddubsw",
2921                                         int_x86_ssse3_pmadd_ub_sw,
2922                                         int_x86_ssse3_pmadd_ub_sw_128>;
2923 defm PMULHRSW    : SS3I_binop_rm_int_16<0x0B, "pmulhrsw",
2924                                         int_x86_ssse3_pmul_hr_sw,
2925                                         int_x86_ssse3_pmul_hr_sw_128, 1>;
2926 defm PSHUFB      : SS3I_binop_rm_int_8 <0x00, "pshufb",
2927                                         int_x86_ssse3_pshuf_b,
2928                                         int_x86_ssse3_pshuf_b_128>;
2929 defm PSIGNB      : SS3I_binop_rm_int_8 <0x08, "psignb",
2930                                         int_x86_ssse3_psign_b,
2931                                         int_x86_ssse3_psign_b_128>;
2932 defm PSIGNW      : SS3I_binop_rm_int_16<0x09, "psignw",
2933                                         int_x86_ssse3_psign_w,
2934                                         int_x86_ssse3_psign_w_128>;
2935 defm PSIGND      : SS3I_binop_rm_int_32<0x0A, "psignd",
2936                                         int_x86_ssse3_psign_d,
2937                                         int_x86_ssse3_psign_d_128>;
2938
2939 let Constraints = "$src1 = $dst" in {
2940   def PALIGNR64rr  : SS3AI<0x0F, MRMSrcReg, (outs VR64:$dst),
2941                            (ins VR64:$src1, VR64:$src2, i8imm:$src3),
2942                            "palignr\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2943                            []>;
2944   def PALIGNR64rm  : SS3AI<0x0F, MRMSrcMem, (outs VR64:$dst),
2945                            (ins VR64:$src1, i64mem:$src2, i8imm:$src3),
2946                            "palignr\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2947                            []>;
2948
2949   def PALIGNR128rr : SS3AI<0x0F, MRMSrcReg, (outs VR128:$dst),
2950                            (ins VR128:$src1, VR128:$src2, i8imm:$src3),
2951                            "palignr\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2952                            []>, OpSize;
2953   def PALIGNR128rm : SS3AI<0x0F, MRMSrcMem, (outs VR128:$dst),
2954                            (ins VR128:$src1, i128mem:$src2, i8imm:$src3),
2955                            "palignr\t{$src3, $src2, $dst|$dst, $src2, $src3}",
2956                            []>, OpSize;
2957 }
2958
2959 // palignr patterns.
2960 def : Pat<(int_x86_ssse3_palign_r VR64:$src1, VR64:$src2, (i8 imm:$src3)),
2961           (PALIGNR64rr VR64:$src1, VR64:$src2, (BYTE_imm imm:$src3))>,
2962           Requires<[HasSSSE3]>;
2963 def : Pat<(int_x86_ssse3_palign_r VR64:$src1,
2964                                       (memop64 addr:$src2),
2965                                       (i8 imm:$src3)),
2966           (PALIGNR64rm VR64:$src1, addr:$src2, (BYTE_imm imm:$src3))>,
2967           Requires<[HasSSSE3]>;
2968
2969 def : Pat<(int_x86_ssse3_palign_r_128 VR128:$src1, VR128:$src2, (i8 imm:$src3)),
2970           (PALIGNR128rr VR128:$src1, VR128:$src2, (BYTE_imm imm:$src3))>,
2971           Requires<[HasSSSE3]>;
2972 def : Pat<(int_x86_ssse3_palign_r_128 VR128:$src1,
2973                                       (memopv2i64 addr:$src2),
2974                                       (i8 imm:$src3)),
2975           (PALIGNR128rm VR128:$src1, addr:$src2, (BYTE_imm imm:$src3))>,
2976           Requires<[HasSSSE3]>;
2977
2978 let AddedComplexity = 5 in {
2979 def : Pat<(v4i32 (palign:$src3 VR128:$src1, VR128:$src2)),
2980           (PALIGNR128rr VR128:$src2, VR128:$src1,
2981                         (SHUFFLE_get_palign_imm VR128:$src3))>,
2982       Requires<[HasSSSE3]>;
2983 def : Pat<(v4f32 (palign:$src3 VR128:$src1, VR128:$src2)),
2984           (PALIGNR128rr VR128:$src2, VR128:$src1,
2985                         (SHUFFLE_get_palign_imm VR128:$src3))>,
2986       Requires<[HasSSSE3]>;
2987 def : Pat<(v8i16 (palign:$src3 VR128:$src1, VR128:$src2)),
2988           (PALIGNR128rr VR128:$src2, VR128:$src1,
2989                         (SHUFFLE_get_palign_imm VR128:$src3))>,
2990       Requires<[HasSSSE3]>;
2991 def : Pat<(v16i8 (palign:$src3 VR128:$src1, VR128:$src2)),
2992           (PALIGNR128rr VR128:$src2, VR128:$src1,
2993                         (SHUFFLE_get_palign_imm VR128:$src3))>,
2994       Requires<[HasSSSE3]>;
2995 }
2996
2997 def : Pat<(X86pshufb VR128:$src, VR128:$mask),
2998           (PSHUFBrr128 VR128:$src, VR128:$mask)>, Requires<[HasSSSE3]>;
2999 def : Pat<(X86pshufb VR128:$src, (bc_v16i8 (memopv2i64 addr:$mask))),
3000           (PSHUFBrm128 VR128:$src, addr:$mask)>, Requires<[HasSSSE3]>;
3001
3002 //===---------------------------------------------------------------------===//
3003 // Non-Instruction Patterns
3004 //===---------------------------------------------------------------------===//
3005
3006 // extload f32 -> f64.  This matches load+fextend because we have a hack in
3007 // the isel (PreprocessForFPConvert) that can introduce loads after dag
3008 // combine.
3009 // Since these loads aren't folded into the fextend, we have to match it
3010 // explicitly here.
3011 let Predicates = [HasSSE2] in
3012  def : Pat<(fextend (loadf32 addr:$src)),
3013            (CVTSS2SDrm addr:$src)>;
3014
3015 // bit_convert
3016 let Predicates = [HasSSE2] in {
3017   def : Pat<(v2i64 (bitconvert (v4i32 VR128:$src))), (v2i64 VR128:$src)>;
3018   def : Pat<(v2i64 (bitconvert (v8i16 VR128:$src))), (v2i64 VR128:$src)>;
3019   def : Pat<(v2i64 (bitconvert (v16i8 VR128:$src))), (v2i64 VR128:$src)>;
3020   def : Pat<(v2i64 (bitconvert (v2f64 VR128:$src))), (v2i64 VR128:$src)>;
3021   def : Pat<(v2i64 (bitconvert (v4f32 VR128:$src))), (v2i64 VR128:$src)>;
3022   def : Pat<(v4i32 (bitconvert (v2i64 VR128:$src))), (v4i32 VR128:$src)>;
3023   def : Pat<(v4i32 (bitconvert (v8i16 VR128:$src))), (v4i32 VR128:$src)>;
3024   def : Pat<(v4i32 (bitconvert (v16i8 VR128:$src))), (v4i32 VR128:$src)>;
3025   def : Pat<(v4i32 (bitconvert (v2f64 VR128:$src))), (v4i32 VR128:$src)>;
3026   def : Pat<(v4i32 (bitconvert (v4f32 VR128:$src))), (v4i32 VR128:$src)>;
3027   def : Pat<(v8i16 (bitconvert (v2i64 VR128:$src))), (v8i16 VR128:$src)>;
3028   def : Pat<(v8i16 (bitconvert (v4i32 VR128:$src))), (v8i16 VR128:$src)>;
3029   def : Pat<(v8i16 (bitconvert (v16i8 VR128:$src))), (v8i16 VR128:$src)>;
3030   def : Pat<(v8i16 (bitconvert (v2f64 VR128:$src))), (v8i16 VR128:$src)>;
3031   def : Pat<(v8i16 (bitconvert (v4f32 VR128:$src))), (v8i16 VR128:$src)>;
3032   def : Pat<(v16i8 (bitconvert (v2i64 VR128:$src))), (v16i8 VR128:$src)>;
3033   def : Pat<(v16i8 (bitconvert (v4i32 VR128:$src))), (v16i8 VR128:$src)>;
3034   def : Pat<(v16i8 (bitconvert (v8i16 VR128:$src))), (v16i8 VR128:$src)>;
3035   def : Pat<(v16i8 (bitconvert (v2f64 VR128:$src))), (v16i8 VR128:$src)>;
3036   def : Pat<(v16i8 (bitconvert (v4f32 VR128:$src))), (v16i8 VR128:$src)>;
3037   def : Pat<(v4f32 (bitconvert (v2i64 VR128:$src))), (v4f32 VR128:$src)>;
3038   def : Pat<(v4f32 (bitconvert (v4i32 VR128:$src))), (v4f32 VR128:$src)>;
3039   def : Pat<(v4f32 (bitconvert (v8i16 VR128:$src))), (v4f32 VR128:$src)>;
3040   def : Pat<(v4f32 (bitconvert (v16i8 VR128:$src))), (v4f32 VR128:$src)>;
3041   def : Pat<(v4f32 (bitconvert (v2f64 VR128:$src))), (v4f32 VR128:$src)>;
3042   def : Pat<(v2f64 (bitconvert (v2i64 VR128:$src))), (v2f64 VR128:$src)>;
3043   def : Pat<(v2f64 (bitconvert (v4i32 VR128:$src))), (v2f64 VR128:$src)>;
3044   def : Pat<(v2f64 (bitconvert (v8i16 VR128:$src))), (v2f64 VR128:$src)>;
3045   def : Pat<(v2f64 (bitconvert (v16i8 VR128:$src))), (v2f64 VR128:$src)>;
3046   def : Pat<(v2f64 (bitconvert (v4f32 VR128:$src))), (v2f64 VR128:$src)>;
3047 }
3048
3049 // Move scalar to XMM zero-extended
3050 // movd to XMM register zero-extends
3051 let AddedComplexity = 15 in {
3052 // Zeroing a VR128 then do a MOVS{S|D} to the lower bits.
3053 def : Pat<(v2f64 (X86vzmovl (v2f64 (scalar_to_vector FR64:$src)))),
3054           (MOVLSD2PDrr (V_SET0), FR64:$src)>, Requires<[HasSSE2]>;
3055 def : Pat<(v4f32 (X86vzmovl (v4f32 (scalar_to_vector FR32:$src)))),
3056           (MOVLSS2PSrr (V_SET0), FR32:$src)>, Requires<[HasSSE1]>;
3057 def : Pat<(v4f32 (X86vzmovl (v4f32 VR128:$src))),
3058           (MOVLPSrr (V_SET0), VR128:$src)>, Requires<[HasSSE1]>;
3059 def : Pat<(v4i32 (X86vzmovl (v4i32 VR128:$src))),
3060           (MOVLPSrr (V_SET0), VR128:$src)>, Requires<[HasSSE1]>;
3061 }
3062
3063 // Splat v2f64 / v2i64
3064 let AddedComplexity = 10 in {
3065 def : Pat<(splat_lo (v2f64 VR128:$src), (undef)),
3066           (UNPCKLPDrr VR128:$src, VR128:$src)>,   Requires<[HasSSE2]>;
3067 def : Pat<(unpckh (v2f64 VR128:$src), (undef)),
3068           (UNPCKHPDrr VR128:$src, VR128:$src)>,   Requires<[HasSSE2]>;
3069 def : Pat<(splat_lo (v2i64 VR128:$src), (undef)),
3070           (PUNPCKLQDQrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3071 def : Pat<(unpckh (v2i64 VR128:$src), (undef)),
3072           (PUNPCKHQDQrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3073 }
3074
3075 // Special unary SHUFPSrri case.
3076 def : Pat<(v4f32 (pshufd:$src3 VR128:$src1, (undef))),
3077           (SHUFPSrri VR128:$src1, VR128:$src1,
3078                      (SHUFFLE_get_shuf_imm VR128:$src3))>,
3079       Requires<[HasSSE1]>;
3080 let AddedComplexity = 5 in
3081 def : Pat<(v4f32 (pshufd:$src2 VR128:$src1, (undef))),
3082           (PSHUFDri VR128:$src1, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3083       Requires<[HasSSE2]>;
3084 // Special unary SHUFPDrri case.
3085 def : Pat<(v2i64 (pshufd:$src3 VR128:$src1, (undef))),
3086           (SHUFPDrri VR128:$src1, VR128:$src1,
3087                      (SHUFFLE_get_shuf_imm VR128:$src3))>,
3088       Requires<[HasSSE2]>;
3089 // Special unary SHUFPDrri case.
3090 def : Pat<(v2f64 (pshufd:$src3 VR128:$src1, (undef))),
3091           (SHUFPDrri VR128:$src1, VR128:$src1,
3092                      (SHUFFLE_get_shuf_imm VR128:$src3))>,
3093       Requires<[HasSSE2]>;
3094 // Unary v4f32 shuffle with PSHUF* in order to fold a load.
3095 def : Pat<(pshufd:$src2 (bc_v4i32 (memopv4f32 addr:$src1)), (undef)),
3096           (PSHUFDmi addr:$src1, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3097       Requires<[HasSSE2]>;
3098
3099 // Special binary v4i32 shuffle cases with SHUFPS.
3100 def : Pat<(v4i32 (shufp:$src3 VR128:$src1, (v4i32 VR128:$src2))),
3101           (SHUFPSrri VR128:$src1, VR128:$src2,
3102                      (SHUFFLE_get_shuf_imm VR128:$src3))>,
3103            Requires<[HasSSE2]>;
3104 def : Pat<(v4i32 (shufp:$src3 VR128:$src1, (bc_v4i32 (memopv2i64 addr:$src2)))),
3105           (SHUFPSrmi VR128:$src1, addr:$src2,
3106                     (SHUFFLE_get_shuf_imm VR128:$src3))>,
3107            Requires<[HasSSE2]>;
3108 // Special binary v2i64 shuffle cases using SHUFPDrri.
3109 def : Pat<(v2i64 (shufp:$src3 VR128:$src1, VR128:$src2)),
3110           (SHUFPDrri VR128:$src1, VR128:$src2,
3111                      (SHUFFLE_get_shuf_imm VR128:$src3))>,
3112           Requires<[HasSSE2]>;
3113
3114 // vector_shuffle v1, <undef>, <0, 0, 1, 1, ...>
3115 let AddedComplexity = 15 in {
3116 def : Pat<(v4i32 (unpckl_undef:$src2 VR128:$src, (undef))),
3117           (PSHUFDri VR128:$src, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3118           Requires<[OptForSpeed, HasSSE2]>;
3119 def : Pat<(v4f32 (unpckl_undef:$src2 VR128:$src, (undef))),
3120           (PSHUFDri VR128:$src, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3121           Requires<[OptForSpeed, HasSSE2]>;
3122 }
3123 let AddedComplexity = 10 in {
3124 def : Pat<(v4f32 (unpckl_undef VR128:$src, (undef))),
3125           (UNPCKLPSrr VR128:$src, VR128:$src)>, Requires<[HasSSE1]>;
3126 def : Pat<(v16i8 (unpckl_undef VR128:$src, (undef))),
3127           (PUNPCKLBWrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3128 def : Pat<(v8i16 (unpckl_undef VR128:$src, (undef))),
3129           (PUNPCKLWDrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3130 def : Pat<(v4i32 (unpckl_undef VR128:$src, (undef))),
3131           (PUNPCKLDQrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3132 }
3133
3134 // vector_shuffle v1, <undef>, <2, 2, 3, 3, ...>
3135 let AddedComplexity = 15 in {
3136 def : Pat<(v4i32 (unpckh_undef:$src2 VR128:$src, (undef))),
3137           (PSHUFDri VR128:$src, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3138           Requires<[OptForSpeed, HasSSE2]>;
3139 def : Pat<(v4f32 (unpckh_undef:$src2 VR128:$src, (undef))),
3140           (PSHUFDri VR128:$src, (SHUFFLE_get_shuf_imm VR128:$src2))>,
3141           Requires<[OptForSpeed, HasSSE2]>;
3142 }
3143 let AddedComplexity = 10 in {
3144 def : Pat<(v4f32 (unpckh_undef VR128:$src, (undef))),
3145           (UNPCKHPSrr VR128:$src, VR128:$src)>, Requires<[HasSSE1]>;
3146 def : Pat<(v16i8 (unpckh_undef VR128:$src, (undef))),
3147           (PUNPCKHBWrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3148 def : Pat<(v8i16 (unpckh_undef VR128:$src, (undef))),
3149           (PUNPCKHWDrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3150 def : Pat<(v4i32 (unpckh_undef VR128:$src, (undef))),
3151           (PUNPCKHDQrr VR128:$src, VR128:$src)>, Requires<[HasSSE2]>;
3152 }
3153
3154 let AddedComplexity = 20 in {
3155 // vector_shuffle v1, v2 <0, 1, 4, 5> using MOVLHPS
3156 def : Pat<(v4i32 (movlhps VR128:$src1, VR128:$src2)),
3157           (MOVLHPSrr VR128:$src1, VR128:$src2)>;
3158
3159 // vector_shuffle v1, v2 <6, 7, 2, 3> using MOVHLPS
3160 def : Pat<(v4i32 (movhlps VR128:$src1, VR128:$src2)),
3161           (MOVHLPSrr VR128:$src1, VR128:$src2)>;
3162
3163 // vector_shuffle v1, undef <2, ?, ?, ?> using MOVHLPS
3164 def : Pat<(v4f32 (movhlps_undef VR128:$src1, (undef))),
3165           (MOVHLPSrr VR128:$src1, VR128:$src1)>;
3166 def : Pat<(v4i32 (movhlps_undef VR128:$src1, (undef))),
3167           (MOVHLPSrr VR128:$src1, VR128:$src1)>;
3168 }
3169
3170 let AddedComplexity = 20 in {
3171 // vector_shuffle v1, (load v2) <4, 5, 2, 3> using MOVLPS
3172 def : Pat<(v4f32 (movlp VR128:$src1, (load addr:$src2))),
3173           (MOVLPSrm VR128:$src1, addr:$src2)>, Requires<[HasSSE1]>;
3174 def : Pat<(v2f64 (movlp VR128:$src1, (load addr:$src2))),
3175           (MOVLPDrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3176 def : Pat<(v4i32 (movlp VR128:$src1, (load addr:$src2))),
3177           (MOVLPSrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3178 def : Pat<(v2i64 (movlp VR128:$src1, (load addr:$src2))),
3179           (MOVLPDrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3180 }
3181
3182 // (store (vector_shuffle (load addr), v2, <4, 5, 2, 3>), addr) using MOVLPS
3183 def : Pat<(store (v4f32 (movlp (load addr:$src1), VR128:$src2)), addr:$src1),
3184           (MOVLPSmr addr:$src1, VR128:$src2)>, Requires<[HasSSE1]>;
3185 def : Pat<(store (v2f64 (movlp (load addr:$src1), VR128:$src2)), addr:$src1),
3186           (MOVLPDmr addr:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3187 def : Pat<(store (v4i32 (movlp (bc_v4i32 (loadv2i64 addr:$src1)), VR128:$src2)),
3188                  addr:$src1),
3189           (MOVLPSmr addr:$src1, VR128:$src2)>, Requires<[HasSSE1]>;
3190 def : Pat<(store (v2i64 (movlp (load addr:$src1), VR128:$src2)), addr:$src1),
3191           (MOVLPDmr addr:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3192
3193 let AddedComplexity = 15 in {
3194 // Setting the lowest element in the vector.
3195 def : Pat<(v4i32 (movl VR128:$src1, VR128:$src2)),
3196           (MOVLPSrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3197 def : Pat<(v2i64 (movl VR128:$src1, VR128:$src2)),
3198           (MOVLPDrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3199
3200 // vector_shuffle v1, v2 <4, 5, 2, 3> using MOVLPDrr (movsd)
3201 def : Pat<(v4f32 (movlp VR128:$src1, VR128:$src2)),
3202           (MOVLPDrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3203 def : Pat<(v4i32 (movlp VR128:$src1, VR128:$src2)),
3204           (MOVLPDrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3205 }
3206
3207 // vector_shuffle v1, v2 <4, 5, 2, 3> using SHUFPSrri (we prefer movsd, but
3208 // fall back to this for SSE1)
3209 def : Pat<(v4f32 (movlp:$src3 VR128:$src1, (v4f32 VR128:$src2))),
3210           (SHUFPSrri VR128:$src2, VR128:$src1,
3211                      (SHUFFLE_get_shuf_imm VR128:$src3))>, Requires<[HasSSE1]>;
3212
3213 // Set lowest element and zero upper elements.
3214 let AddedComplexity = 15 in
3215 def : Pat<(v2f64 (movl immAllZerosV_bc, VR128:$src)),
3216           (MOVZPQILo2PQIrr VR128:$src)>, Requires<[HasSSE2]>;
3217 def : Pat<(v2f64 (X86vzmovl (v2f64 VR128:$src))),
3218           (MOVZPQILo2PQIrr VR128:$src)>, Requires<[HasSSE2]>;
3219
3220 // Some special case pandn patterns.
3221 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v4i32 immAllOnesV))),
3222                   VR128:$src2)),
3223           (PANDNrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3224 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v8i16 immAllOnesV))),
3225                   VR128:$src2)),
3226           (PANDNrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3227 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v16i8 immAllOnesV))),
3228                   VR128:$src2)),
3229           (PANDNrr VR128:$src1, VR128:$src2)>, Requires<[HasSSE2]>;
3230
3231 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v4i32 immAllOnesV))),
3232                   (memop addr:$src2))),
3233           (PANDNrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3234 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v8i16 immAllOnesV))),
3235                   (memop addr:$src2))),
3236           (PANDNrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3237 def : Pat<(v2i64 (and (xor VR128:$src1, (bc_v2i64 (v16i8 immAllOnesV))),
3238                   (memop addr:$src2))),
3239           (PANDNrm VR128:$src1, addr:$src2)>, Requires<[HasSSE2]>;
3240
3241 // vector -> vector casts
3242 def : Pat<(v4f32 (sint_to_fp (v4i32 VR128:$src))),
3243           (Int_CVTDQ2PSrr VR128:$src)>, Requires<[HasSSE2]>;
3244 def : Pat<(v4i32 (fp_to_sint (v4f32 VR128:$src))),
3245           (Int_CVTTPS2DQrr VR128:$src)>, Requires<[HasSSE2]>;
3246 def : Pat<(v2f64 (sint_to_fp (v2i32 VR64:$src))),
3247           (Int_CVTPI2PDrr VR64:$src)>, Requires<[HasSSE2]>;
3248 def : Pat<(v2i32 (fp_to_sint (v2f64 VR128:$src))),
3249           (Int_CVTTPD2PIrr VR128:$src)>, Requires<[HasSSE2]>;
3250
3251 // Use movaps / movups for SSE integer load / store (one byte shorter).
3252 def : Pat<(alignedloadv4i32 addr:$src),
3253           (MOVAPSrm addr:$src)>, Requires<[HasSSE1]>;
3254 def : Pat<(loadv4i32 addr:$src),
3255           (MOVUPSrm addr:$src)>, Requires<[HasSSE1]>;
3256 def : Pat<(alignedloadv2i64 addr:$src),
3257           (MOVAPSrm addr:$src)>, Requires<[HasSSE2]>;
3258 def : Pat<(loadv2i64 addr:$src),
3259           (MOVUPSrm addr:$src)>, Requires<[HasSSE2]>;
3260
3261 def : Pat<(alignedstore (v2i64 VR128:$src), addr:$dst),
3262           (MOVAPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3263 def : Pat<(alignedstore (v4i32 VR128:$src), addr:$dst),
3264           (MOVAPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3265 def : Pat<(alignedstore (v8i16 VR128:$src), addr:$dst),
3266           (MOVAPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3267 def : Pat<(alignedstore (v16i8 VR128:$src), addr:$dst),
3268           (MOVAPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3269 def : Pat<(store (v2i64 VR128:$src), addr:$dst),
3270           (MOVUPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3271 def : Pat<(store (v4i32 VR128:$src), addr:$dst),
3272           (MOVUPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3273 def : Pat<(store (v8i16 VR128:$src), addr:$dst),
3274           (MOVUPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3275 def : Pat<(store (v16i8 VR128:$src), addr:$dst),
3276           (MOVUPSmr addr:$dst, VR128:$src)>, Requires<[HasSSE2]>;
3277
3278 //===----------------------------------------------------------------------===//
3279 // SSE4.1 Instructions
3280 //===----------------------------------------------------------------------===//
3281
3282 multiclass sse41_fp_unop_rm<bits<8> opcps, bits<8> opcpd,
3283                             string OpcodeStr,
3284                             Intrinsic V4F32Int,
3285                             Intrinsic V2F64Int> {
3286   // Intrinsic operation, reg.
3287   // Vector intrinsic operation, reg
3288   def PSr_Int : SS4AIi8<opcps, MRMSrcReg,
3289                     (outs VR128:$dst), (ins VR128:$src1, i32i8imm:$src2),
3290                     !strconcat(OpcodeStr,
3291                     "ps\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3292                     [(set VR128:$dst, (V4F32Int VR128:$src1, imm:$src2))]>,
3293                     OpSize;
3294
3295   // Vector intrinsic operation, mem
3296   def PSm_Int : Ii8<opcps, MRMSrcMem,
3297                     (outs VR128:$dst), (ins f128mem:$src1, i32i8imm:$src2),
3298                     !strconcat(OpcodeStr,
3299                     "ps\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3300                     [(set VR128:$dst,
3301                           (V4F32Int (memopv4f32 addr:$src1),imm:$src2))]>,
3302                     TA, OpSize,
3303                 Requires<[HasSSE41]>;
3304
3305   // Vector intrinsic operation, reg
3306   def PDr_Int : SS4AIi8<opcpd, MRMSrcReg,
3307                     (outs VR128:$dst), (ins VR128:$src1, i32i8imm:$src2),
3308                     !strconcat(OpcodeStr,
3309                     "pd\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3310                     [(set VR128:$dst, (V2F64Int VR128:$src1, imm:$src2))]>,
3311                     OpSize;
3312
3313   // Vector intrinsic operation, mem
3314   def PDm_Int : SS4AIi8<opcpd, MRMSrcMem,
3315                     (outs VR128:$dst), (ins f128mem:$src1, i32i8imm:$src2),
3316                     !strconcat(OpcodeStr,
3317                     "pd\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3318                     [(set VR128:$dst,
3319                           (V2F64Int (memopv2f64 addr:$src1),imm:$src2))]>,
3320                     OpSize;
3321 }
3322
3323 let Constraints = "$src1 = $dst" in {
3324 multiclass sse41_fp_binop_rm<bits<8> opcss, bits<8> opcsd,
3325                             string OpcodeStr,
3326                             Intrinsic F32Int,
3327                             Intrinsic F64Int> {
3328   // Intrinsic operation, reg.
3329   def SSr_Int : SS4AIi8<opcss, MRMSrcReg,
3330                     (outs VR128:$dst),
3331                                  (ins VR128:$src1, VR128:$src2, i32i8imm:$src3),
3332                     !strconcat(OpcodeStr,
3333                     "ss\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3334                     [(set VR128:$dst,
3335                             (F32Int VR128:$src1, VR128:$src2, imm:$src3))]>,
3336                     OpSize;
3337
3338   // Intrinsic operation, mem.
3339   def SSm_Int : SS4AIi8<opcss, MRMSrcMem,
3340                     (outs VR128:$dst),
3341                                 (ins VR128:$src1, ssmem:$src2, i32i8imm:$src3),
3342                     !strconcat(OpcodeStr,
3343                     "ss\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3344                     [(set VR128:$dst,
3345                          (F32Int VR128:$src1, sse_load_f32:$src2, imm:$src3))]>,
3346                     OpSize;
3347
3348   // Intrinsic operation, reg.
3349   def SDr_Int : SS4AIi8<opcsd, MRMSrcReg,
3350                     (outs VR128:$dst),
3351                             (ins VR128:$src1, VR128:$src2, i32i8imm:$src3),
3352                     !strconcat(OpcodeStr,
3353                     "sd\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3354                     [(set VR128:$dst,
3355                             (F64Int VR128:$src1, VR128:$src2, imm:$src3))]>,
3356                     OpSize;
3357
3358   // Intrinsic operation, mem.
3359   def SDm_Int : SS4AIi8<opcsd, MRMSrcMem,
3360                     (outs VR128:$dst),
3361                             (ins VR128:$src1, sdmem:$src2, i32i8imm:$src3),
3362                     !strconcat(OpcodeStr,
3363                     "sd\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3364                     [(set VR128:$dst,
3365                         (F64Int VR128:$src1, sse_load_f64:$src2, imm:$src3))]>,
3366                     OpSize;
3367 }
3368 }
3369
3370 // FP round - roundss, roundps, roundsd, roundpd
3371 defm ROUND  : sse41_fp_unop_rm<0x08, 0x09, "round",
3372                                int_x86_sse41_round_ps, int_x86_sse41_round_pd>;
3373 defm ROUND  : sse41_fp_binop_rm<0x0A, 0x0B, "round",
3374                                int_x86_sse41_round_ss, int_x86_sse41_round_sd>;
3375
3376 // SS41I_unop_rm_int_v16 - SSE 4.1 unary operator whose type is v8i16.
3377 multiclass SS41I_unop_rm_int_v16<bits<8> opc, string OpcodeStr,
3378                                  Intrinsic IntId128> {
3379   def rr128 : SS48I<opc, MRMSrcReg, (outs VR128:$dst),
3380                     (ins VR128:$src),
3381                     !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3382                     [(set VR128:$dst, (IntId128 VR128:$src))]>, OpSize;
3383   def rm128 : SS48I<opc, MRMSrcMem, (outs VR128:$dst),
3384                      (ins i128mem:$src),
3385                      !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3386                      [(set VR128:$dst,
3387                        (IntId128
3388                        (bitconvert (memopv8i16 addr:$src))))]>, OpSize;
3389 }
3390
3391 defm PHMINPOSUW : SS41I_unop_rm_int_v16 <0x41, "phminposuw",
3392                                          int_x86_sse41_phminposuw>;
3393
3394 /// SS41I_binop_rm_int - Simple SSE 4.1 binary operator
3395 let Constraints = "$src1 = $dst" in {
3396   multiclass SS41I_binop_rm_int<bits<8> opc, string OpcodeStr,
3397                                 Intrinsic IntId128, bit Commutable = 0> {
3398     def rr : SS48I<opc, MRMSrcReg, (outs VR128:$dst),
3399                    (ins VR128:$src1, VR128:$src2),
3400                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3401                    [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
3402                    OpSize {
3403       let isCommutable = Commutable;
3404     }
3405     def rm : SS48I<opc, MRMSrcMem, (outs VR128:$dst),
3406                    (ins VR128:$src1, i128mem:$src2),
3407                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3408                    [(set VR128:$dst,
3409                      (IntId128 VR128:$src1,
3410                       (bitconvert (memopv16i8 addr:$src2))))]>, OpSize;
3411   }
3412 }
3413
3414 defm PCMPEQQ      : SS41I_binop_rm_int<0x29, "pcmpeqq",
3415                                        int_x86_sse41_pcmpeqq, 1>;
3416 defm PACKUSDW     : SS41I_binop_rm_int<0x2B, "packusdw",
3417                                        int_x86_sse41_packusdw, 0>;
3418 defm PMINSB       : SS41I_binop_rm_int<0x38, "pminsb",
3419                                        int_x86_sse41_pminsb, 1>;
3420 defm PMINSD       : SS41I_binop_rm_int<0x39, "pminsd",
3421                                        int_x86_sse41_pminsd, 1>;
3422 defm PMINUD       : SS41I_binop_rm_int<0x3B, "pminud",
3423                                        int_x86_sse41_pminud, 1>;
3424 defm PMINUW       : SS41I_binop_rm_int<0x3A, "pminuw",
3425                                        int_x86_sse41_pminuw, 1>;
3426 defm PMAXSB       : SS41I_binop_rm_int<0x3C, "pmaxsb",
3427                                        int_x86_sse41_pmaxsb, 1>;
3428 defm PMAXSD       : SS41I_binop_rm_int<0x3D, "pmaxsd",
3429                                        int_x86_sse41_pmaxsd, 1>;
3430 defm PMAXUD       : SS41I_binop_rm_int<0x3F, "pmaxud",
3431                                        int_x86_sse41_pmaxud, 1>;
3432 defm PMAXUW       : SS41I_binop_rm_int<0x3E, "pmaxuw",
3433                                        int_x86_sse41_pmaxuw, 1>;
3434
3435 defm PMULDQ       : SS41I_binop_rm_int<0x28, "pmuldq", int_x86_sse41_pmuldq, 1>;
3436
3437 def : Pat<(v2i64 (X86pcmpeqq VR128:$src1, VR128:$src2)),
3438           (PCMPEQQrr VR128:$src1, VR128:$src2)>;
3439 def : Pat<(v2i64 (X86pcmpeqq VR128:$src1, (memop addr:$src2))),
3440           (PCMPEQQrm VR128:$src1, addr:$src2)>;
3441
3442 /// SS41I_binop_rm_int - Simple SSE 4.1 binary operator
3443 let Constraints = "$src1 = $dst" in {
3444   multiclass SS41I_binop_patint<bits<8> opc, string OpcodeStr, ValueType OpVT,
3445                                 SDNode OpNode, Intrinsic IntId128,
3446                                 bit Commutable = 0> {
3447     def rr : SS48I<opc, MRMSrcReg, (outs VR128:$dst),
3448                    (ins VR128:$src1, VR128:$src2),
3449                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3450                    [(set VR128:$dst, (OpNode (OpVT VR128:$src1),
3451                                                    VR128:$src2))]>, OpSize {
3452       let isCommutable = Commutable;
3453     }
3454     def rr_int : SS48I<opc, MRMSrcReg, (outs VR128:$dst),
3455                       (ins VR128:$src1, VR128:$src2),
3456                       !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3457                       [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
3458                       OpSize {
3459       let isCommutable = Commutable;
3460     }
3461     def rm : SS48I<opc, MRMSrcMem, (outs VR128:$dst),
3462                    (ins VR128:$src1, i128mem:$src2),
3463                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3464                    [(set VR128:$dst,
3465                      (OpVT (OpNode VR128:$src1, (memop addr:$src2))))]>, OpSize;
3466     def rm_int : SS48I<opc, MRMSrcMem, (outs VR128:$dst),
3467                        (ins VR128:$src1, i128mem:$src2),
3468                        !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3469                        [(set VR128:$dst,
3470                         (IntId128 VR128:$src1, (memop addr:$src2)))]>,
3471                        OpSize;
3472   }
3473 }
3474 defm PMULLD       : SS41I_binop_patint<0x40, "pmulld", v4i32, mul,
3475                                        int_x86_sse41_pmulld, 1>;
3476
3477 /// SS41I_binop_rmi_int - SSE 4.1 binary operator with 8-bit immediate
3478 let Constraints = "$src1 = $dst" in {
3479   multiclass SS41I_binop_rmi_int<bits<8> opc, string OpcodeStr,
3480                                  Intrinsic IntId128, bit Commutable = 0> {
3481     def rri : SS4AIi8<opc, MRMSrcReg, (outs VR128:$dst),
3482                     (ins VR128:$src1, VR128:$src2, i32i8imm:$src3),
3483                     !strconcat(OpcodeStr,
3484                      "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3485                     [(set VR128:$dst,
3486                       (IntId128 VR128:$src1, VR128:$src2, imm:$src3))]>,
3487                     OpSize {
3488       let isCommutable = Commutable;
3489     }
3490     def rmi : SS4AIi8<opc, MRMSrcMem, (outs VR128:$dst),
3491                     (ins VR128:$src1, i128mem:$src2, i32i8imm:$src3),
3492                     !strconcat(OpcodeStr,
3493                      "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3494                     [(set VR128:$dst,
3495                       (IntId128 VR128:$src1,
3496                        (bitconvert (memopv16i8 addr:$src2)), imm:$src3))]>,
3497                     OpSize;
3498   }
3499 }
3500
3501 defm BLENDPS      : SS41I_binop_rmi_int<0x0C, "blendps",
3502                                         int_x86_sse41_blendps, 0>;
3503 defm BLENDPD      : SS41I_binop_rmi_int<0x0D, "blendpd",
3504                                         int_x86_sse41_blendpd, 0>;
3505 defm PBLENDW      : SS41I_binop_rmi_int<0x0E, "pblendw",
3506                                         int_x86_sse41_pblendw, 0>;
3507 defm DPPS         : SS41I_binop_rmi_int<0x40, "dpps",
3508                                         int_x86_sse41_dpps, 1>;
3509 defm DPPD         : SS41I_binop_rmi_int<0x41, "dppd",
3510                                         int_x86_sse41_dppd, 1>;
3511 defm MPSADBW      : SS41I_binop_rmi_int<0x42, "mpsadbw",
3512                                         int_x86_sse41_mpsadbw, 1>;
3513
3514
3515 /// SS41I_ternary_int - SSE 4.1 ternary operator
3516 let Uses = [XMM0], Constraints = "$src1 = $dst" in {
3517   multiclass SS41I_ternary_int<bits<8> opc, string OpcodeStr, Intrinsic IntId> {
3518     def rr0 : SS48I<opc, MRMSrcReg, (outs VR128:$dst),
3519                     (ins VR128:$src1, VR128:$src2),
3520                     !strconcat(OpcodeStr,
3521                      "\t{%xmm0, $src2, $dst|$dst, $src2, %xmm0}"),
3522                     [(set VR128:$dst, (IntId VR128:$src1, VR128:$src2, XMM0))]>,
3523                     OpSize;
3524
3525     def rm0 : SS48I<opc, MRMSrcMem, (outs VR128:$dst),
3526                     (ins VR128:$src1, i128mem:$src2),
3527                     !strconcat(OpcodeStr,
3528                      "\t{%xmm0, $src2, $dst|$dst, $src2, %xmm0}"),
3529                     [(set VR128:$dst,
3530                       (IntId VR128:$src1,
3531                        (bitconvert (memopv16i8 addr:$src2)), XMM0))]>, OpSize;
3532   }
3533 }
3534
3535 defm BLENDVPD     : SS41I_ternary_int<0x15, "blendvpd", int_x86_sse41_blendvpd>;
3536 defm BLENDVPS     : SS41I_ternary_int<0x14, "blendvps", int_x86_sse41_blendvps>;
3537 defm PBLENDVB     : SS41I_ternary_int<0x10, "pblendvb", int_x86_sse41_pblendvb>;
3538
3539
3540 multiclass SS41I_binop_rm_int8<bits<8> opc, string OpcodeStr, Intrinsic IntId> {
3541   def rr : SS48I<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
3542                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3543                  [(set VR128:$dst, (IntId VR128:$src))]>, OpSize;
3544
3545   def rm : SS48I<opc, MRMSrcMem, (outs VR128:$dst), (ins i64mem:$src),
3546                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3547        [(set VR128:$dst,
3548          (IntId (bitconvert (v2i64 (scalar_to_vector (loadi64 addr:$src))))))]>,
3549        OpSize;
3550 }
3551
3552 defm PMOVSXBW   : SS41I_binop_rm_int8<0x20, "pmovsxbw", int_x86_sse41_pmovsxbw>;
3553 defm PMOVSXWD   : SS41I_binop_rm_int8<0x23, "pmovsxwd", int_x86_sse41_pmovsxwd>;
3554 defm PMOVSXDQ   : SS41I_binop_rm_int8<0x25, "pmovsxdq", int_x86_sse41_pmovsxdq>;
3555 defm PMOVZXBW   : SS41I_binop_rm_int8<0x30, "pmovzxbw", int_x86_sse41_pmovzxbw>;
3556 defm PMOVZXWD   : SS41I_binop_rm_int8<0x33, "pmovzxwd", int_x86_sse41_pmovzxwd>;
3557 defm PMOVZXDQ   : SS41I_binop_rm_int8<0x35, "pmovzxdq", int_x86_sse41_pmovzxdq>;
3558
3559 // Common patterns involving scalar load.
3560 def : Pat<(int_x86_sse41_pmovsxbw (vzmovl_v2i64 addr:$src)),
3561           (PMOVSXBWrm addr:$src)>, Requires<[HasSSE41]>;
3562 def : Pat<(int_x86_sse41_pmovsxbw (vzload_v2i64 addr:$src)),
3563           (PMOVSXBWrm addr:$src)>, Requires<[HasSSE41]>;
3564
3565 def : Pat<(int_x86_sse41_pmovsxwd (vzmovl_v2i64 addr:$src)),
3566           (PMOVSXWDrm addr:$src)>, Requires<[HasSSE41]>;
3567 def : Pat<(int_x86_sse41_pmovsxwd (vzload_v2i64 addr:$src)),
3568           (PMOVSXWDrm addr:$src)>, Requires<[HasSSE41]>;
3569
3570 def : Pat<(int_x86_sse41_pmovsxdq (vzmovl_v2i64 addr:$src)),
3571           (PMOVSXDQrm addr:$src)>, Requires<[HasSSE41]>;
3572 def : Pat<(int_x86_sse41_pmovsxdq (vzload_v2i64 addr:$src)),
3573           (PMOVSXDQrm addr:$src)>, Requires<[HasSSE41]>;
3574
3575 def : Pat<(int_x86_sse41_pmovzxbw (vzmovl_v2i64 addr:$src)),
3576           (PMOVZXBWrm addr:$src)>, Requires<[HasSSE41]>;
3577 def : Pat<(int_x86_sse41_pmovzxbw (vzload_v2i64 addr:$src)),
3578           (PMOVZXBWrm addr:$src)>, Requires<[HasSSE41]>;
3579
3580 def : Pat<(int_x86_sse41_pmovzxwd (vzmovl_v2i64 addr:$src)),
3581           (PMOVZXWDrm addr:$src)>, Requires<[HasSSE41]>;
3582 def : Pat<(int_x86_sse41_pmovzxwd (vzload_v2i64 addr:$src)),
3583           (PMOVZXWDrm addr:$src)>, Requires<[HasSSE41]>;
3584
3585 def : Pat<(int_x86_sse41_pmovzxdq (vzmovl_v2i64 addr:$src)),
3586           (PMOVZXDQrm addr:$src)>, Requires<[HasSSE41]>;
3587 def : Pat<(int_x86_sse41_pmovzxdq (vzload_v2i64 addr:$src)),
3588           (PMOVZXDQrm addr:$src)>, Requires<[HasSSE41]>;
3589
3590
3591 multiclass SS41I_binop_rm_int4<bits<8> opc, string OpcodeStr, Intrinsic IntId> {
3592   def rr : SS48I<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
3593                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3594                  [(set VR128:$dst, (IntId VR128:$src))]>, OpSize;
3595
3596   def rm : SS48I<opc, MRMSrcMem, (outs VR128:$dst), (ins i32mem:$src),
3597                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3598        [(set VR128:$dst,
3599          (IntId (bitconvert (v4i32 (scalar_to_vector (loadi32 addr:$src))))))]>,
3600           OpSize;
3601 }
3602
3603 defm PMOVSXBD   : SS41I_binop_rm_int4<0x21, "pmovsxbd", int_x86_sse41_pmovsxbd>;
3604 defm PMOVSXWQ   : SS41I_binop_rm_int4<0x24, "pmovsxwq", int_x86_sse41_pmovsxwq>;
3605 defm PMOVZXBD   : SS41I_binop_rm_int4<0x31, "pmovzxbd", int_x86_sse41_pmovzxbd>;
3606 defm PMOVZXWQ   : SS41I_binop_rm_int4<0x34, "pmovzxwq", int_x86_sse41_pmovzxwq>;
3607
3608 // Common patterns involving scalar load
3609 def : Pat<(int_x86_sse41_pmovsxbd (vzmovl_v4i32 addr:$src)),
3610           (PMOVSXBDrm addr:$src)>, Requires<[HasSSE41]>;
3611 def : Pat<(int_x86_sse41_pmovsxwq (vzmovl_v4i32 addr:$src)),
3612           (PMOVSXWQrm addr:$src)>, Requires<[HasSSE41]>;
3613
3614 def : Pat<(int_x86_sse41_pmovzxbd (vzmovl_v4i32 addr:$src)),
3615           (PMOVZXBDrm addr:$src)>, Requires<[HasSSE41]>;
3616 def : Pat<(int_x86_sse41_pmovzxwq (vzmovl_v4i32 addr:$src)),
3617           (PMOVZXWQrm addr:$src)>, Requires<[HasSSE41]>;
3618
3619
3620 multiclass SS41I_binop_rm_int2<bits<8> opc, string OpcodeStr, Intrinsic IntId> {
3621   def rr : SS48I<opc, MRMSrcReg, (outs VR128:$dst), (ins VR128:$src),
3622                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3623                  [(set VR128:$dst, (IntId VR128:$src))]>, OpSize;
3624
3625   // Expecting a i16 load any extended to i32 value.
3626   def rm : SS48I<opc, MRMSrcMem, (outs VR128:$dst), (ins i16mem:$src),
3627                  !strconcat(OpcodeStr, "\t{$src, $dst|$dst, $src}"),
3628                  [(set VR128:$dst, (IntId (bitconvert
3629                      (v4i32 (scalar_to_vector (loadi16_anyext addr:$src))))))]>,
3630                  OpSize;
3631 }
3632
3633 defm PMOVSXBQ   : SS41I_binop_rm_int2<0x22, "pmovsxbq", int_x86_sse41_pmovsxbq>;
3634 defm PMOVZXBQ   : SS41I_binop_rm_int2<0x32, "pmovzxbq", int_x86_sse41_pmovzxbq>;
3635
3636 // Common patterns involving scalar load
3637 def : Pat<(int_x86_sse41_pmovsxbq
3638             (bitconvert (v4i32 (X86vzmovl
3639                              (v4i32 (scalar_to_vector (loadi32 addr:$src))))))),
3640           (PMOVSXBQrm addr:$src)>, Requires<[HasSSE41]>;
3641
3642 def : Pat<(int_x86_sse41_pmovzxbq
3643             (bitconvert (v4i32 (X86vzmovl
3644                              (v4i32 (scalar_to_vector (loadi32 addr:$src))))))),
3645           (PMOVZXBQrm addr:$src)>, Requires<[HasSSE41]>;
3646
3647
3648 /// SS41I_binop_ext8 - SSE 4.1 extract 8 bits to 32 bit reg or 8 bit mem
3649 multiclass SS41I_extract8<bits<8> opc, string OpcodeStr> {
3650   def rr : SS4AIi8<opc, MRMDestReg, (outs GR32:$dst),
3651                  (ins VR128:$src1, i32i8imm:$src2),
3652                  !strconcat(OpcodeStr,
3653                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3654                  [(set GR32:$dst, (X86pextrb (v16i8 VR128:$src1), imm:$src2))]>,
3655                  OpSize;
3656   def mr : SS4AIi8<opc, MRMDestMem, (outs),
3657                  (ins i8mem:$dst, VR128:$src1, i32i8imm:$src2),
3658                  !strconcat(OpcodeStr,
3659                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3660                  []>, OpSize;
3661 // FIXME:
3662 // There's an AssertZext in the way of writing the store pattern
3663 // (store (i8 (trunc (X86pextrb (v16i8 VR128:$src1), imm:$src2))), addr:$dst)
3664 }
3665
3666 defm PEXTRB      : SS41I_extract8<0x14, "pextrb">;
3667
3668
3669 /// SS41I_extract16 - SSE 4.1 extract 16 bits to memory destination
3670 multiclass SS41I_extract16<bits<8> opc, string OpcodeStr> {
3671   def mr : SS4AIi8<opc, MRMDestMem, (outs),
3672                  (ins i16mem:$dst, VR128:$src1, i32i8imm:$src2),
3673                  !strconcat(OpcodeStr,
3674                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3675                  []>, OpSize;
3676 // FIXME:
3677 // There's an AssertZext in the way of writing the store pattern
3678 // (store (i16 (trunc (X86pextrw (v16i8 VR128:$src1), imm:$src2))), addr:$dst)
3679 }
3680
3681 defm PEXTRW      : SS41I_extract16<0x15, "pextrw">;
3682
3683
3684 /// SS41I_extract32 - SSE 4.1 extract 32 bits to int reg or memory destination
3685 multiclass SS41I_extract32<bits<8> opc, string OpcodeStr> {
3686   def rr : SS4AIi8<opc, MRMDestReg, (outs GR32:$dst),
3687                  (ins VR128:$src1, i32i8imm:$src2),
3688                  !strconcat(OpcodeStr,
3689                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3690                  [(set GR32:$dst,
3691                   (extractelt (v4i32 VR128:$src1), imm:$src2))]>, OpSize;
3692   def mr : SS4AIi8<opc, MRMDestMem, (outs),
3693                  (ins i32mem:$dst, VR128:$src1, i32i8imm:$src2),
3694                  !strconcat(OpcodeStr,
3695                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3696                  [(store (extractelt (v4i32 VR128:$src1), imm:$src2),
3697                           addr:$dst)]>, OpSize;
3698 }
3699
3700 defm PEXTRD      : SS41I_extract32<0x16, "pextrd">;
3701
3702
3703 /// SS41I_extractf32 - SSE 4.1 extract 32 bits fp value to int reg or memory
3704 /// destination
3705 multiclass SS41I_extractf32<bits<8> opc, string OpcodeStr> {
3706   def rr : SS4AIi8<opc, MRMDestReg, (outs GR32:$dst),
3707                  (ins VR128:$src1, i32i8imm:$src2),
3708                  !strconcat(OpcodeStr,
3709                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3710                  [(set GR32:$dst,
3711                     (extractelt (bc_v4i32 (v4f32 VR128:$src1)), imm:$src2))]>,
3712            OpSize;
3713   def mr : SS4AIi8<opc, MRMDestMem, (outs),
3714                  (ins f32mem:$dst, VR128:$src1, i32i8imm:$src2),
3715                  !strconcat(OpcodeStr,
3716                   "\t{$src2, $src1, $dst|$dst, $src1, $src2}"),
3717                  [(store (extractelt (bc_v4i32 (v4f32 VR128:$src1)), imm:$src2),
3718                           addr:$dst)]>, OpSize;
3719 }
3720
3721 defm EXTRACTPS   : SS41I_extractf32<0x17, "extractps">;
3722
3723 // Also match an EXTRACTPS store when the store is done as f32 instead of i32.
3724 def : Pat<(store (f32 (bitconvert (extractelt (bc_v4i32 (v4f32 VR128:$src1)),
3725                                               imm:$src2))),
3726                  addr:$dst),
3727           (EXTRACTPSmr addr:$dst, VR128:$src1, imm:$src2)>,
3728          Requires<[HasSSE41]>;
3729
3730 let Constraints = "$src1 = $dst" in {
3731   multiclass SS41I_insert8<bits<8> opc, string OpcodeStr> {
3732     def rr : SS4AIi8<opc, MRMSrcReg, (outs VR128:$dst),
3733                    (ins VR128:$src1, GR32:$src2, i32i8imm:$src3),
3734                    !strconcat(OpcodeStr,
3735                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3736                    [(set VR128:$dst,
3737                      (X86pinsrb VR128:$src1, GR32:$src2, imm:$src3))]>, OpSize;
3738     def rm : SS4AIi8<opc, MRMSrcMem, (outs VR128:$dst),
3739                    (ins VR128:$src1, i8mem:$src2, i32i8imm:$src3),
3740                    !strconcat(OpcodeStr,
3741                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3742                    [(set VR128:$dst,
3743                      (X86pinsrb VR128:$src1, (extloadi8 addr:$src2),
3744                                 imm:$src3))]>, OpSize;
3745   }
3746 }
3747
3748 defm PINSRB      : SS41I_insert8<0x20, "pinsrb">;
3749
3750 let Constraints = "$src1 = $dst" in {
3751   multiclass SS41I_insert32<bits<8> opc, string OpcodeStr> {
3752     def rr : SS4AIi8<opc, MRMSrcReg, (outs VR128:$dst),
3753                    (ins VR128:$src1, GR32:$src2, i32i8imm:$src3),
3754                    !strconcat(OpcodeStr,
3755                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3756                    [(set VR128:$dst,
3757                      (v4i32 (insertelt VR128:$src1, GR32:$src2, imm:$src3)))]>,
3758                    OpSize;
3759     def rm : SS4AIi8<opc, MRMSrcMem, (outs VR128:$dst),
3760                    (ins VR128:$src1, i32mem:$src2, i32i8imm:$src3),
3761                    !strconcat(OpcodeStr,
3762                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3763                    [(set VR128:$dst,
3764                      (v4i32 (insertelt VR128:$src1, (loadi32 addr:$src2),
3765                                        imm:$src3)))]>, OpSize;
3766   }
3767 }
3768
3769 defm PINSRD      : SS41I_insert32<0x22, "pinsrd">;
3770
3771 // insertps has a few different modes, there's the first two here below which
3772 // are optimized inserts that won't zero arbitrary elements in the destination
3773 // vector. The next one matches the intrinsic and could zero arbitrary elements
3774 // in the target vector.
3775 let Constraints = "$src1 = $dst" in {
3776   multiclass SS41I_insertf32<bits<8> opc, string OpcodeStr> {
3777     def rr : SS4AIi8<opc, MRMSrcReg, (outs VR128:$dst),
3778                    (ins VR128:$src1, VR128:$src2, i32i8imm:$src3),
3779                    !strconcat(OpcodeStr,
3780                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3781                    [(set VR128:$dst,
3782                      (X86insrtps VR128:$src1, VR128:$src2, imm:$src3))]>,
3783       OpSize;
3784     def rm : SS4AIi8<opc, MRMSrcMem, (outs VR128:$dst),
3785                    (ins VR128:$src1, f32mem:$src2, i32i8imm:$src3),
3786                    !strconcat(OpcodeStr,
3787                     "\t{$src3, $src2, $dst|$dst, $src2, $src3}"),
3788                    [(set VR128:$dst,
3789                      (X86insrtps VR128:$src1,
3790                                 (v4f32 (scalar_to_vector (loadf32 addr:$src2))),
3791                                  imm:$src3))]>, OpSize;
3792   }
3793 }
3794
3795 defm INSERTPS    : SS41I_insertf32<0x21, "insertps">;
3796
3797 def : Pat<(int_x86_sse41_insertps VR128:$src1, VR128:$src2, imm:$src3),
3798           (INSERTPSrr VR128:$src1, VR128:$src2, imm:$src3)>;
3799
3800 // ptest instruction we'll lower to this in X86ISelLowering primarily from
3801 // the intel intrinsic that corresponds to this.
3802 let Defs = [EFLAGS] in {
3803 def PTESTrr : SS48I<0x17, MRMSrcReg, (outs), (ins VR128:$src1, VR128:$src2),
3804                     "ptest \t{$src2, $src1|$src1, $src2}",
3805                     [(X86ptest VR128:$src1, VR128:$src2),
3806                       (implicit EFLAGS)]>, OpSize;
3807 def PTESTrm : SS48I<0x17, MRMSrcMem, (outs), (ins VR128:$src1, i128mem:$src2),
3808                     "ptest \t{$src2, $src1|$src1, $src2}",
3809                     [(X86ptest VR128:$src1, (load addr:$src2)),
3810                         (implicit EFLAGS)]>, OpSize;
3811 }
3812
3813 def MOVNTDQArm : SS48I<0x2A, MRMSrcMem, (outs VR128:$dst), (ins i128mem:$src),
3814                        "movntdqa\t{$src, $dst|$dst, $src}",
3815                        [(set VR128:$dst, (int_x86_sse41_movntdqa addr:$src))]>,
3816                        OpSize;
3817
3818
3819 //===----------------------------------------------------------------------===//
3820 // SSE4.2 Instructions
3821 //===----------------------------------------------------------------------===//
3822
3823 /// SS42I_binop_rm_int - Simple SSE 4.2 binary operator
3824 let Constraints = "$src1 = $dst" in {
3825   multiclass SS42I_binop_rm_int<bits<8> opc, string OpcodeStr,
3826                                 Intrinsic IntId128, bit Commutable = 0> {
3827     def rr : SS428I<opc, MRMSrcReg, (outs VR128:$dst),
3828                    (ins VR128:$src1, VR128:$src2),
3829                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3830                    [(set VR128:$dst, (IntId128 VR128:$src1, VR128:$src2))]>,
3831                    OpSize {
3832       let isCommutable = Commutable;
3833     }
3834     def rm : SS428I<opc, MRMSrcMem, (outs VR128:$dst),
3835                    (ins VR128:$src1, i128mem:$src2),
3836                    !strconcat(OpcodeStr, "\t{$src2, $dst|$dst, $src2}"),
3837                    [(set VR128:$dst,
3838                      (IntId128 VR128:$src1,
3839                       (bitconvert (memopv16i8 addr:$src2))))]>, OpSize;
3840   }
3841 }
3842
3843 defm PCMPGTQ      : SS42I_binop_rm_int<0x37, "pcmpgtq", int_x86_sse42_pcmpgtq>;
3844
3845 def : Pat<(v2i64 (X86pcmpgtq VR128:$src1, VR128:$src2)),
3846           (PCMPGTQrr VR128:$src1, VR128:$src2)>;
3847 def : Pat<(v2i64 (X86pcmpgtq VR128:$src1, (memop addr:$src2))),
3848           (PCMPGTQrm VR128:$src1, addr:$src2)>;
3849
3850 // crc intrinsic instruction
3851 // This set of instructions are only rm, the only difference is the size
3852 // of r and m.
3853 let Constraints = "$src1 = $dst" in {
3854   def CRC32m8  : SS42FI<0xF0, MRMSrcMem, (outs GR32:$dst),
3855                       (ins GR32:$src1, i8mem:$src2),
3856                       "crc32 \t{$src2, $src1|$src1, $src2}",
3857                        [(set GR32:$dst,
3858                          (int_x86_sse42_crc32_8 GR32:$src1,
3859                          (load addr:$src2)))]>, OpSize;
3860   def CRC32r8  : SS42FI<0xF0, MRMSrcReg, (outs GR32:$dst),
3861                       (ins GR32:$src1, GR8:$src2),
3862                       "crc32 \t{$src2, $src1|$src1, $src2}",
3863                        [(set GR32:$dst,
3864                          (int_x86_sse42_crc32_8 GR32:$src1, GR8:$src2))]>,
3865                          OpSize;
3866   def CRC32m16  : SS42FI<0xF1, MRMSrcMem, (outs GR32:$dst),
3867                       (ins GR32:$src1, i16mem:$src2),
3868                       "crc32 \t{$src2, $src1|$src1, $src2}",
3869                        [(set GR32:$dst,
3870                          (int_x86_sse42_crc32_16 GR32:$src1,
3871                          (load addr:$src2)))]>,
3872                          OpSize;
3873   def CRC32r16  : SS42FI<0xF1, MRMSrcReg, (outs GR32:$dst),
3874                       (ins GR32:$src1, GR16:$src2),
3875                       "crc32 \t{$src2, $src1|$src1, $src2}",
3876                        [(set GR32:$dst,
3877                          (int_x86_sse42_crc32_16 GR32:$src1, GR16:$src2))]>,
3878                          OpSize;
3879   def CRC32m32  : SS42FI<0xF1, MRMSrcMem, (outs GR32:$dst),
3880                       (ins GR32:$src1, i32mem:$src2),
3881                       "crc32 \t{$src2, $src1|$src1, $src2}",
3882                        [(set GR32:$dst,
3883                          (int_x86_sse42_crc32_32 GR32:$src1,
3884                          (load addr:$src2)))]>, OpSize;
3885   def CRC32r32  : SS42FI<0xF1, MRMSrcReg, (outs GR32:$dst),
3886                       (ins GR32:$src1, GR32:$src2),
3887                       "crc32 \t{$src2, $src1|$src1, $src2}",
3888                        [(set GR32:$dst,
3889                          (int_x86_sse42_crc32_32 GR32:$src1, GR32:$src2))]>,
3890                          OpSize;
3891   def CRC64m64  : SS42FI<0xF0, MRMSrcMem, (outs GR64:$dst),
3892                       (ins GR64:$src1, i64mem:$src2),
3893                       "crc32 \t{$src2, $src1|$src1, $src2}",
3894                        [(set GR64:$dst,
3895                          (int_x86_sse42_crc32_64 GR64:$src1,
3896                          (load addr:$src2)))]>,
3897                          OpSize, REX_W;
3898   def CRC64r64  : SS42FI<0xF0, MRMSrcReg, (outs GR64:$dst),
3899                       (ins GR64:$src1, GR64:$src2),
3900                       "crc32 \t{$src2, $src1|$src1, $src2}",
3901                        [(set GR64:$dst,
3902                          (int_x86_sse42_crc32_64 GR64:$src1, GR64:$src2))]>,
3903                          OpSize, REX_W;
3904 }
3905
3906 // String/text processing instructions.
3907 let Defs = [EFLAGS], usesCustomInserter = 1 in {
3908 def PCMPISTRM128REG : SS42AI<0, Pseudo, (outs VR128:$dst),
3909   (ins VR128:$src1, VR128:$src2, i8imm:$src3),
3910   "#PCMPISTRM128rr PSEUDO!",
3911   [(set VR128:$dst, (int_x86_sse42_pcmpistrm128 VR128:$src1, VR128:$src2,
3912                                                 imm:$src3))]>, OpSize;
3913 def PCMPISTRM128MEM : SS42AI<0, Pseudo, (outs VR128:$dst),
3914   (ins VR128:$src1, i128mem:$src2, i8imm:$src3),
3915   "#PCMPISTRM128rm PSEUDO!",
3916   [(set VR128:$dst, (int_x86_sse42_pcmpistrm128 VR128:$src1, (load addr:$src2),
3917                                                 imm:$src3))]>, OpSize;
3918 }
3919
3920 let Defs = [XMM0, EFLAGS] in {
3921 def PCMPISTRM128rr : SS42AI<0x62, MRMSrcReg, (outs),
3922   (ins VR128:$src1, VR128:$src2, i8imm:$src3),
3923    "pcmpistrm\t{$src3, $src2, $src1|$src1, $src2, $src3}", []>, OpSize;
3924 def PCMPISTRM128rm : SS42AI<0x62, MRMSrcMem, (outs),
3925   (ins VR128:$src1, i128mem:$src2, i8imm:$src3),
3926   "pcmpistrm\t{$src3, $src2, $src1|$src1, $src2, $src3}", []>, OpSize;
3927 }
3928
3929 let Defs = [EFLAGS], Uses = [EAX, EDX], usesCustomInserter = 1 in {
3930 def PCMPESTRM128REG : SS42AI<0, Pseudo, (outs VR128:$dst),
3931   (ins VR128:$src1, VR128:$src3, i8imm:$src5),
3932   "#PCMPESTRM128rr PSEUDO!",
3933   [(set VR128:$dst, 
3934         (int_x86_sse42_pcmpestrm128 
3935          VR128:$src1, EAX, VR128:$src3, EDX, imm:$src5))]>, OpSize;
3936
3937 def PCMPESTRM128MEM : SS42AI<0, Pseudo, (outs VR128:$dst),
3938   (ins VR128:$src1, i128mem:$src3, i8imm:$src5),
3939   "#PCMPESTRM128rm PSEUDO!",
3940   [(set VR128:$dst, (int_x86_sse42_pcmpestrm128 
3941                      VR128:$src1, EAX, (load addr:$src3), EDX, imm:$src5))]>, 
3942   OpSize;
3943 }
3944
3945 let Defs = [XMM0, EFLAGS], Uses = [EAX, EDX] in {
3946 def PCMPESTRM128rr : SS42AI<0x60, MRMSrcReg, (outs),
3947   (ins VR128:$src1, VR128:$src3, i8imm:$src5),
3948   "pcmpestrm\t{$src5, $src3, $src1|$src1, $src3, $src5}", []>, OpSize;
3949 def PCMPESTRM128rm : SS42AI<0x60, MRMSrcMem, (outs),
3950   (ins VR128:$src1, i128mem:$src3, i8imm:$src5),
3951   "pcmpestrm\t{$src5, $src3, $src1|$src1, $src3, $src5}", []>, OpSize;
3952 }
3953
3954 let Defs = [ECX, EFLAGS] in {
3955   multiclass SS42AI_pcmpistri<Intrinsic IntId128> {
3956     def rr : SS42AI<0x63, MRMSrcReg, (outs), 
3957       (ins VR128:$src1, VR128:$src2, i8imm:$src3),
3958       "pcmpistri\t{$src3, $src2, $src1|$src1, $src2, $src3}",
3959       [(set ECX, (IntId128 VR128:$src1, VR128:$src2, imm:$src3)),
3960        (implicit EFLAGS)]>, OpSize;
3961     def rm : SS42AI<0x63, MRMSrcMem, (outs),
3962       (ins VR128:$src1, i128mem:$src2, i8imm:$src3),
3963       "pcmpistri\t{$src3, $src2, $src1|$src1, $src2, $src3}",
3964       [(set ECX, (IntId128 VR128:$src1, (load addr:$src2), imm:$src3)),
3965        (implicit EFLAGS)]>, OpSize;
3966   }
3967 }
3968
3969 defm PCMPISTRI  : SS42AI_pcmpistri<int_x86_sse42_pcmpistri128>;
3970 defm PCMPISTRIA : SS42AI_pcmpistri<int_x86_sse42_pcmpistria128>;
3971 defm PCMPISTRIC : SS42AI_pcmpistri<int_x86_sse42_pcmpistric128>;
3972 defm PCMPISTRIO : SS42AI_pcmpistri<int_x86_sse42_pcmpistrio128>;
3973 defm PCMPISTRIS : SS42AI_pcmpistri<int_x86_sse42_pcmpistris128>;
3974 defm PCMPISTRIZ : SS42AI_pcmpistri<int_x86_sse42_pcmpistriz128>;
3975
3976 let Defs = [ECX, EFLAGS] in {
3977 let Uses = [EAX, EDX] in {
3978   multiclass SS42AI_pcmpestri<Intrinsic IntId128> {
3979     def rr : SS42AI<0x61, MRMSrcReg, (outs),
3980       (ins VR128:$src1, VR128:$src3, i8imm:$src5),
3981       "pcmpestri\t{$src5, $src3, $src1|$src1, $src3, $src5}",
3982       [(set ECX, (IntId128 VR128:$src1, EAX, VR128:$src3, EDX, imm:$src5)),
3983        (implicit EFLAGS)]>, OpSize;
3984     def rm : SS42AI<0x61, MRMSrcMem, (outs),
3985       (ins VR128:$src1, i128mem:$src3, i8imm:$src5),
3986        "pcmpestri\t{$src5, $src3, $src1|$src1, $src3, $src5}",
3987        [(set ECX, 
3988              (IntId128 VR128:$src1, EAX, (load addr:$src3), EDX, imm:$src5)),
3989         (implicit EFLAGS)]>, OpSize;
3990   }
3991 }
3992 }
3993
3994 defm PCMPESTRI  : SS42AI_pcmpestri<int_x86_sse42_pcmpestri128>;
3995 defm PCMPESTRIA : SS42AI_pcmpestri<int_x86_sse42_pcmpestria128>;
3996 defm PCMPESTRIC : SS42AI_pcmpestri<int_x86_sse42_pcmpestric128>;
3997 defm PCMPESTRIO : SS42AI_pcmpestri<int_x86_sse42_pcmpestrio128>;
3998 defm PCMPESTRIS : SS42AI_pcmpestri<int_x86_sse42_pcmpestris128>;
3999 defm PCMPESTRIZ : SS42AI_pcmpestri<int_x86_sse42_pcmpestriz128>;