Upgrade GCC from 4.4.5 to 4.4.6 on the vendor branch
[dragonfly.git] / contrib / gcc-4.4 / gcc / config / i386 / sse.md
1 ;; GCC machine description for SSE instructions
2 ;; Copyright (C) 2005, 2006, 2007, 2008, 2009
3 ;; Free Software Foundation, Inc.
4 ;;
5 ;; This file is part of GCC.
6 ;;
7 ;; GCC is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 3, or (at your option)
10 ;; any later version.
11 ;;
12 ;; GCC is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 ;; GNU General Public License for more details.
16 ;;
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GCC; see the file COPYING3.  If not see
19 ;; <http://www.gnu.org/licenses/>.
20
21
22 ;; 16 byte integral modes handled by SSE, minus TImode, which gets
23 ;; special-cased for TARGET_64BIT.
24 (define_mode_iterator SSEMODEI [V16QI V8HI V4SI V2DI])
25
26 ;; All 16-byte vector modes handled by SSE
27 (define_mode_iterator SSEMODE [V16QI V8HI V4SI V2DI V4SF V2DF])
28
29 ;; 32 byte integral vector modes handled by AVX
30 (define_mode_iterator AVX256MODEI [V32QI V16HI V8SI V4DI])
31
32 ;; All 32-byte vector modes handled by AVX
33 (define_mode_iterator AVX256MODE [V32QI V16HI V8SI V4DI V8SF V4DF])
34
35 ;; All QI vector modes handled by AVX
36 (define_mode_iterator AVXMODEQI [V32QI V16QI])
37
38 ;; All DI vector modes handled by AVX
39 (define_mode_iterator AVXMODEDI [V4DI V2DI])
40
41 ;; All vector modes handled by AVX
42 (define_mode_iterator AVXMODE [V16QI V8HI V4SI V2DI V4SF V2DF V32QI V16HI V8SI V4DI V8SF V4DF])
43
44 ;; Mix-n-match
45 (define_mode_iterator SSEMODE12 [V16QI V8HI])
46 (define_mode_iterator SSEMODE24 [V8HI V4SI])
47 (define_mode_iterator SSEMODE14 [V16QI V4SI])
48 (define_mode_iterator SSEMODE124 [V16QI V8HI V4SI])
49 (define_mode_iterator SSEMODE248 [V8HI V4SI V2DI])
50 (define_mode_iterator SSEMODE1248 [V16QI V8HI V4SI V2DI])
51 (define_mode_iterator SSEMODEF4 [SF DF V4SF V2DF])
52 (define_mode_iterator SSEMODEF2P [V4SF V2DF])
53
54 (define_mode_iterator AVX256MODEF2P [V8SF V4DF])
55 (define_mode_iterator AVX256MODE2P [V8SI V8SF V4DF])
56 (define_mode_iterator AVX256MODE4P [V4DI V4DF])
57 (define_mode_iterator AVX256MODE8P [V8SI V8SF])
58 (define_mode_iterator AVXMODEF2P [V4SF V2DF V8SF V4DF])
59 (define_mode_iterator AVXMODEF4P [V4SF V4DF])
60 (define_mode_iterator AVXMODEDCVTDQ2PS [V4SF V8SF])
61 (define_mode_iterator AVXMODEDCVTPS2DQ [V4SI V8SI])
62
63 ;; Int-float size matches
64 (define_mode_iterator SSEMODE4S [V4SF V4SI])
65 (define_mode_iterator SSEMODE2D [V2DF V2DI])
66
67 ;; Modes handled by integer vcond pattern
68 (define_mode_iterator SSEMODE124C8 [V16QI V8HI V4SI
69                                     (V2DI "TARGET_SSE4_2 || TARGET_SSE5")])
70
71 ;; Mapping from float mode to required SSE level
72 (define_mode_attr sse [(SF "sse") (DF "sse2") (V4SF "sse") (V2DF "sse2")])
73
74 ;; Mapping from integer vector mode to mnemonic suffix
75 (define_mode_attr ssevecsize [(V16QI "b") (V8HI "w") (V4SI "d") (V2DI "q")])
76
77 ;; Mapping of the sse5 suffix
78 (define_mode_attr ssemodesuffixf4 [(SF "ss") (DF "sd")
79                                    (V4SF "ps") (V2DF "pd")])
80 (define_mode_attr ssemodesuffixf2s [(SF "ss") (DF "sd")
81                                     (V4SF "ss") (V2DF "sd")])
82 (define_mode_attr ssemodesuffixf2c [(V4SF "s") (V2DF "d")])
83
84 ;; Mapping of the max integer size for sse5 rotate immediate constraint
85 (define_mode_attr sserotatemax [(V16QI "7") (V8HI "15") (V4SI "31") (V2DI "63")])
86
87 ;; Mapping of vector modes back to the scalar modes
88 (define_mode_attr ssescalarmode [(V4SF "SF") (V2DF "DF")
89                                  (V16QI "QI") (V8HI "HI")
90                                  (V4SI "SI") (V2DI "DI")])
91
92 ;; Mapping of vector modes to a vector mode of double size
93 (define_mode_attr ssedoublesizemode [(V2DF "V4DF") (V2DI "V4DI")
94                                      (V4SF "V8SF") (V4SI "V8SI")])
95
96 ;; Number of scalar elements in each vector type
97 (define_mode_attr ssescalarnum [(V4SF "4") (V2DF "2")
98                                 (V16QI "16") (V8HI "8")
99                                 (V4SI "4") (V2DI "2")])
100
101 ;; Mapping for AVX
102 (define_mode_attr avxvecmode
103   [(V16QI "TI") (V8HI "TI") (V4SI "TI") (V2DI "TI") (V4SF "V4SF")
104    (V2DF "V2DF") (V32QI "OI") (V16HI "OI") (V8SI "OI") (V4DI "OI")
105    (V8SF "V8SF") (V4DF "V4DF")])
106 (define_mode_attr avxvecpsmode
107   [(V16QI "V4SF") (V8HI "V4SF") (V4SI "V4SF") (V2DI "V4SF")
108    (V32QI "V8SF") (V16HI "V8SF") (V8SI "V8SF") (V4DI "V8SF")])
109 (define_mode_attr avxhalfvecmode
110   [(V4SF "V2SF") (V32QI "V16QI")  (V16HI "V8HI") (V8SI "V4SI")
111    (V4DI "V2DI") (V8SF "V4SF") (V4DF "V2DF")])
112 (define_mode_attr avxscalarmode
113   [(V16QI "QI") (V8HI "HI") (V4SI "SI") (V4SF "SF") (V2DF "DF")
114    (V8SF "SF") (V4DF "DF")])
115 (define_mode_attr avxcvtvecmode
116   [(V4SF "V4SI") (V8SF "V8SI") (V4SI "V4SF") (V8SI "V8SF")])
117 (define_mode_attr avxpermvecmode
118   [(V2DF "V2DI") (V4SF "V4SI") (V4DF "V4DI") (V8SF "V8SI")])
119 (define_mode_attr avxmodesuffixf2c
120   [(V4SF "s") (V2DF "d") (V8SF "s") (V4DF "d")])
121 (define_mode_attr avxmodesuffixp
122  [(V2DF "pd") (V4SI "si") (V4SF "ps") (V8SF "ps") (V8SI "si")
123   (V4DF "pd")])
124 (define_mode_attr avxmodesuffixs
125  [(V16QI "b") (V8HI "w") (V4SI "d")])
126 (define_mode_attr avxmodesuffix
127   [(V16QI "") (V32QI "256") (V4SI "") (V4SF "") (V2DF "")
128    (V8SI "256") (V8SF "256") (V4DF "256")])
129
130 ;; Mapping of immediate bits for blend instructions
131 (define_mode_attr blendbits
132   [(V8SF "255") (V4SF "15") (V4DF "15") (V2DF "3")])
133
134 ;; Mapping of immediate bits for vpermil instructions
135 (define_mode_attr vpermilbits
136   [(V8SF "255") (V4SF "255") (V4DF "15") (V2DF "3")])
137
138 ;; Mapping of immediate bits for pinsr instructions
139 (define_mode_attr pinsrbits [(V16QI "32768") (V8HI "128") (V4SI "8")])
140
141 ;; Patterns whose name begins with "sse{,2,3}_" are invoked by intrinsics.
142
143 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
144 ;;
145 ;; Move patterns
146 ;;
147 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
148
149 (define_expand "mov<mode>"
150   [(set (match_operand:AVX256MODE 0 "nonimmediate_operand" "")
151         (match_operand:AVX256MODE 1 "nonimmediate_operand" ""))]
152   "TARGET_AVX"
153 {
154   ix86_expand_vector_move (<MODE>mode, operands);
155   DONE;
156 })
157
158 (define_insn "*avx_mov<mode>_internal"
159   [(set (match_operand:AVXMODE 0 "nonimmediate_operand" "=x,x ,m")
160         (match_operand:AVXMODE 1 "nonimmediate_or_sse_const_operand"  "C ,xm,x"))]
161   "TARGET_AVX
162    && (register_operand (operands[0], <MODE>mode)
163        || register_operand (operands[1], <MODE>mode))"
164 {
165   switch (which_alternative)
166     {
167     case 0:
168       return standard_sse_constant_opcode (insn, operands[1]);
169     case 1:
170     case 2:
171       switch (get_attr_mode (insn))
172         {
173         case MODE_V8SF:
174         case MODE_V4SF:
175           return "vmovaps\t{%1, %0|%0, %1}";
176         case MODE_V4DF:
177         case MODE_V2DF:
178           return "vmovapd\t{%1, %0|%0, %1}";
179         default:
180           return "vmovdqa\t{%1, %0|%0, %1}";
181         }
182     default:
183       gcc_unreachable ();
184     }
185 }
186   [(set_attr "type" "sselog1,ssemov,ssemov")
187    (set_attr "prefix" "vex")
188    (set_attr "mode" "<avxvecmode>")])
189
190 ;; All of these patterns are enabled for SSE1 as well as SSE2.
191 ;; This is essential for maintaining stable calling conventions.
192
193 (define_expand "mov<mode>"
194   [(set (match_operand:SSEMODE 0 "nonimmediate_operand" "")
195         (match_operand:SSEMODE 1 "nonimmediate_operand" ""))]
196   "TARGET_SSE"
197 {
198   ix86_expand_vector_move (<MODE>mode, operands);
199   DONE;
200 })
201
202 (define_insn "*mov<mode>_internal"
203   [(set (match_operand:SSEMODE 0 "nonimmediate_operand" "=x,x ,m")
204         (match_operand:SSEMODE 1 "nonimmediate_or_sse_const_operand"  "C ,xm,x"))]
205   "TARGET_SSE
206    && (register_operand (operands[0], <MODE>mode)
207        || register_operand (operands[1], <MODE>mode))"
208 {
209   switch (which_alternative)
210     {
211     case 0:
212       return standard_sse_constant_opcode (insn, operands[1]);
213     case 1:
214     case 2:
215       switch (get_attr_mode (insn))
216         {
217         case MODE_V4SF:
218           return "movaps\t{%1, %0|%0, %1}";
219         case MODE_V2DF:
220           return "movapd\t{%1, %0|%0, %1}";
221         default:
222           return "movdqa\t{%1, %0|%0, %1}";
223         }
224     default:
225       gcc_unreachable ();
226     }
227 }
228   [(set_attr "type" "sselog1,ssemov,ssemov")
229    (set (attr "mode")
230         (cond [(ior (ior (ne (symbol_ref "optimize_function_for_size_p (cfun)") (const_int 0))
231                          (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
232                     (and (eq_attr "alternative" "2")
233                          (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
234                              (const_int 0))))
235                  (const_string "V4SF")
236                (eq (const_string "<MODE>mode") (const_string "V4SFmode"))
237                  (const_string "V4SF")
238                (eq (const_string "<MODE>mode") (const_string "V2DFmode"))
239                  (const_string "V2DF")
240               ]
241           (const_string "TI")))])
242
243 ;; Move a DI from a 32-bit register pair (e.g. %edx:%eax) to an xmm.
244 ;; We'd rather avoid this entirely; if the 32-bit reg pair was loaded
245 ;; from memory, we'd prefer to load the memory directly into the %xmm
246 ;; register.  To facilitate this happy circumstance, this pattern won't
247 ;; split until after register allocation.  If the 64-bit value didn't
248 ;; come from memory, this is the best we can do.  This is much better
249 ;; than storing %edx:%eax into a stack temporary and loading an %xmm
250 ;; from there.
251
252 (define_insn_and_split "movdi_to_sse"
253   [(parallel
254     [(set (match_operand:V4SI 0 "register_operand" "=?x,x")
255           (subreg:V4SI (match_operand:DI 1 "nonimmediate_operand" "r,m") 0))
256      (clobber (match_scratch:V4SI 2 "=&x,X"))])]
257   "!TARGET_64BIT && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES"
258   "#"
259   "&& reload_completed"
260   [(const_int 0)]
261 {
262  if (register_operand (operands[1], DImode))
263    {
264       /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
265          Assemble the 64-bit DImode value in an xmm register.  */
266       emit_insn (gen_sse2_loadld (operands[0], CONST0_RTX (V4SImode),
267                                   gen_rtx_SUBREG (SImode, operands[1], 0)));
268       emit_insn (gen_sse2_loadld (operands[2], CONST0_RTX (V4SImode),
269                                   gen_rtx_SUBREG (SImode, operands[1], 4)));
270       emit_insn (gen_sse2_punpckldq (operands[0], operands[0], operands[2]));
271     }
272  else if (memory_operand (operands[1], DImode))
273       emit_insn (gen_vec_concatv2di (gen_lowpart (V2DImode, operands[0]), operands[1], const0_rtx));
274  else
275       gcc_unreachable ();
276 })
277
278 (define_split
279   [(set (match_operand:V4SF 0 "register_operand" "")
280         (match_operand:V4SF 1 "zero_extended_scalar_load_operand" ""))]
281   "TARGET_SSE && reload_completed"
282   [(set (match_dup 0)
283         (vec_merge:V4SF
284           (vec_duplicate:V4SF (match_dup 1))
285           (match_dup 2)
286           (const_int 1)))]
287 {
288   operands[1] = simplify_gen_subreg (SFmode, operands[1], V4SFmode, 0);
289   operands[2] = CONST0_RTX (V4SFmode);
290 })
291
292 (define_split
293   [(set (match_operand:V2DF 0 "register_operand" "")
294         (match_operand:V2DF 1 "zero_extended_scalar_load_operand" ""))]
295   "TARGET_SSE2 && reload_completed"
296   [(set (match_dup 0) (vec_concat:V2DF (match_dup 1) (match_dup 2)))]
297 {
298   operands[1] = simplify_gen_subreg (DFmode, operands[1], V2DFmode, 0);
299   operands[2] = CONST0_RTX (DFmode);
300 })
301
302 (define_expand "push<mode>1"
303   [(match_operand:AVX256MODE 0 "register_operand" "")]
304   "TARGET_AVX"
305 {
306   ix86_expand_push (<MODE>mode, operands[0]);
307   DONE;
308 })
309
310 (define_expand "push<mode>1"
311   [(match_operand:SSEMODE 0 "register_operand" "")]
312   "TARGET_SSE"
313 {
314   ix86_expand_push (<MODE>mode, operands[0]);
315   DONE;
316 })
317
318 (define_expand "movmisalign<mode>"
319   [(set (match_operand:AVX256MODE 0 "nonimmediate_operand" "")
320         (match_operand:AVX256MODE 1 "nonimmediate_operand" ""))]
321   "TARGET_AVX"
322 {
323   ix86_expand_vector_move_misalign (<MODE>mode, operands);
324   DONE;
325 })
326
327 (define_expand "movmisalign<mode>"
328   [(set (match_operand:SSEMODE 0 "nonimmediate_operand" "")
329         (match_operand:SSEMODE 1 "nonimmediate_operand" ""))]
330   "TARGET_SSE"
331 {
332   ix86_expand_vector_move_misalign (<MODE>mode, operands);
333   DONE;
334 })
335
336 (define_insn "avx_movup<avxmodesuffixf2c><avxmodesuffix>"
337   [(set (match_operand:AVXMODEF2P 0 "nonimmediate_operand" "=x,m")
338         (unspec:AVXMODEF2P
339           [(match_operand:AVXMODEF2P 1 "nonimmediate_operand" "xm,x")]
340           UNSPEC_MOVU))]
341   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)
342    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
343   "vmovup<avxmodesuffixf2c>\t{%1, %0|%0, %1}"
344   [(set_attr "type" "ssemov")
345    (set_attr "prefix" "vex")
346    (set_attr "mode" "<MODE>")])
347
348 (define_insn "sse2_movq128"
349   [(set (match_operand:V2DI 0 "register_operand" "=x")
350         (vec_concat:V2DI
351           (vec_select:DI
352             (match_operand:V2DI 1 "nonimmediate_operand" "xm")
353             (parallel [(const_int 0)]))
354           (const_int 0)))]
355   "TARGET_SSE2"
356   "%vmovq\t{%1, %0|%0, %1}"
357   [(set_attr "type" "ssemov")
358    (set_attr "prefix" "maybe_vex")
359    (set_attr "mode" "TI")])
360
361 (define_insn "<sse>_movup<ssemodesuffixf2c>"
362   [(set (match_operand:SSEMODEF2P 0 "nonimmediate_operand" "=x,m")
363         (unspec:SSEMODEF2P
364           [(match_operand:SSEMODEF2P 1 "nonimmediate_operand" "xm,x")]
365           UNSPEC_MOVU))]
366   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)
367    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
368   "movup<ssemodesuffixf2c>\t{%1, %0|%0, %1}"
369   [(set_attr "type" "ssemov")
370    (set_attr "mode" "<MODE>")])
371
372 (define_insn "avx_movdqu<avxmodesuffix>"
373   [(set (match_operand:AVXMODEQI 0 "nonimmediate_operand" "=x,m")
374         (unspec:AVXMODEQI
375           [(match_operand:AVXMODEQI 1 "nonimmediate_operand" "xm,x")]
376           UNSPEC_MOVU))]
377   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
378   "vmovdqu\t{%1, %0|%0, %1}"
379   [(set_attr "type" "ssemov")
380    (set_attr "prefix" "vex")
381    (set_attr "mode" "<avxvecmode>")])
382
383 (define_insn "sse2_movdqu"
384   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
385         (unspec:V16QI [(match_operand:V16QI 1 "nonimmediate_operand" "xm,x")]
386                       UNSPEC_MOVU))]
387   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
388   "movdqu\t{%1, %0|%0, %1}"
389   [(set_attr "type" "ssemov")
390    (set_attr "prefix_data16" "1")
391    (set_attr "mode" "TI")])
392
393 (define_insn "avx_movnt<mode>"
394   [(set (match_operand:AVXMODEF2P 0 "memory_operand" "=m")
395         (unspec:AVXMODEF2P
396           [(match_operand:AVXMODEF2P 1 "register_operand" "x")]
397           UNSPEC_MOVNT))]
398   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
399   "vmovntp<avxmodesuffixf2c>\t{%1, %0|%0, %1}"
400   [(set_attr "type" "ssemov")
401    (set_attr "prefix" "vex")
402    (set_attr "mode" "<MODE>")])
403
404 (define_insn "<sse>_movnt<mode>"
405   [(set (match_operand:SSEMODEF2P 0 "memory_operand" "=m")
406         (unspec:SSEMODEF2P
407           [(match_operand:SSEMODEF2P 1 "register_operand" "x")]
408           UNSPEC_MOVNT))]
409   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
410   "movntp<ssemodesuffixf2c>\t{%1, %0|%0, %1}"
411   [(set_attr "type" "ssemov")
412    (set_attr "mode" "<MODE>")])
413
414 (define_insn "avx_movnt<mode>"
415   [(set (match_operand:AVXMODEDI 0 "memory_operand" "=m")
416         (unspec:AVXMODEDI
417           [(match_operand:AVXMODEDI 1 "register_operand" "x")]
418           UNSPEC_MOVNT))]
419   "TARGET_AVX"
420   "vmovntdq\t{%1, %0|%0, %1}"
421   [(set_attr "type" "ssecvt")
422    (set_attr "prefix" "vex")
423    (set_attr "mode" "<avxvecmode>")])
424
425 (define_insn "sse2_movntv2di"
426   [(set (match_operand:V2DI 0 "memory_operand" "=m")
427         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")]
428                      UNSPEC_MOVNT))]
429   "TARGET_SSE2"
430   "movntdq\t{%1, %0|%0, %1}"
431   [(set_attr "type" "ssecvt")
432    (set_attr "prefix_data16" "1")
433    (set_attr "mode" "TI")])
434
435 (define_insn "sse2_movntsi"
436   [(set (match_operand:SI 0 "memory_operand" "=m")
437         (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
438                    UNSPEC_MOVNT))]
439   "TARGET_SSE2"
440   "movnti\t{%1, %0|%0, %1}"
441   [(set_attr "type" "ssecvt")
442    (set_attr "mode" "V2DF")])
443
444 (define_insn "avx_lddqu<avxmodesuffix>"
445   [(set (match_operand:AVXMODEQI 0 "register_operand" "=x")
446         (unspec:AVXMODEQI
447           [(match_operand:AVXMODEQI 1 "memory_operand" "m")]
448           UNSPEC_LDDQU))]
449   "TARGET_AVX"
450   "vlddqu\t{%1, %0|%0, %1}"
451   [(set_attr "type" "ssecvt")
452    (set_attr "prefix" "vex")
453    (set_attr "mode" "<avxvecmode>")])
454
455 (define_insn "sse3_lddqu"
456   [(set (match_operand:V16QI 0 "register_operand" "=x")
457         (unspec:V16QI [(match_operand:V16QI 1 "memory_operand" "m")]
458                       UNSPEC_LDDQU))]
459   "TARGET_SSE3"
460   "lddqu\t{%1, %0|%0, %1}"
461   [(set_attr "type" "ssecvt")
462    (set_attr "prefix_rep" "1")
463    (set_attr "mode" "TI")])
464
465 ; Expand patterns for non-temporal stores.  At the moment, only those
466 ; that directly map to insns are defined; it would be possible to
467 ; define patterns for other modes that would expand to several insns.
468
469 (define_expand "storent<mode>"
470   [(set (match_operand:SSEMODEF2P 0 "memory_operand" "")
471         (unspec:SSEMODEF2P
472           [(match_operand:SSEMODEF2P 1 "register_operand" "")]
473           UNSPEC_MOVNT))]
474   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
475   "")
476
477 (define_expand "storent<mode>"
478   [(set (match_operand:MODEF 0 "memory_operand" "")
479         (unspec:MODEF
480           [(match_operand:MODEF 1 "register_operand" "")]
481           UNSPEC_MOVNT))]
482   "TARGET_SSE4A"
483   "")
484
485 (define_expand "storentv2di"
486   [(set (match_operand:V2DI 0 "memory_operand" "")
487         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "")]
488                      UNSPEC_MOVNT))]
489   "TARGET_SSE2"
490   "")
491
492 (define_expand "storentsi"
493   [(set (match_operand:SI 0 "memory_operand" "")
494         (unspec:SI [(match_operand:SI 1 "register_operand" "")]
495                    UNSPEC_MOVNT))]
496   "TARGET_SSE2"
497   "")
498
499 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
500 ;;
501 ;; Parallel floating point arithmetic
502 ;;
503 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
504
505 (define_expand "<code><mode>2"
506   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
507         (absneg:SSEMODEF2P
508           (match_operand:SSEMODEF2P 1 "register_operand" "")))]
509   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
510   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
511
512 (define_expand "<plusminus_insn><mode>3"
513   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "")
514         (plusminus:AVX256MODEF2P
515           (match_operand:AVX256MODEF2P 1 "nonimmediate_operand" "")
516           (match_operand:AVX256MODEF2P 2 "nonimmediate_operand" "")))]
517   "AVX256_VEC_FLOAT_MODE_P (<MODE>mode)"
518   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
519
520 (define_insn "*avx_<plusminus_insn><mode>3"
521   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
522         (plusminus:AVXMODEF2P
523           (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "<comm>x")
524           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
525   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)
526    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
527   "v<plusminus_mnemonic>p<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
528   [(set_attr "type" "sseadd")
529    (set_attr "prefix" "vex")
530    (set_attr "mode" "<avxvecmode>")])
531
532 (define_expand "<plusminus_insn><mode>3"
533   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
534         (plusminus:SSEMODEF2P
535           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "")
536           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "")))]
537   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
538   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
539
540 (define_insn "*<plusminus_insn><mode>3"
541   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
542         (plusminus:SSEMODEF2P
543           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "<comm>0")
544           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
545   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)
546    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
547   "<plusminus_mnemonic>p<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
548   [(set_attr "type" "sseadd")
549    (set_attr "mode" "<MODE>")])
550
551 (define_insn "*avx_vm<plusminus_insn><mode>3"
552   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
553         (vec_merge:SSEMODEF2P
554           (plusminus:SSEMODEF2P
555             (match_operand:SSEMODEF2P 1 "register_operand" "x")
556             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
557           (match_dup 1)
558           (const_int 1)))]
559   "AVX128_VEC_FLOAT_MODE_P (<MODE>mode)"
560   "v<plusminus_mnemonic>s<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
561   [(set_attr "type" "sseadd")
562    (set_attr "prefix" "vex")
563    (set_attr "mode" "<ssescalarmode>")])
564
565 (define_insn "<sse>_vm<plusminus_insn><mode>3"
566   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
567         (vec_merge:SSEMODEF2P
568           (plusminus:SSEMODEF2P
569             (match_operand:SSEMODEF2P 1 "register_operand" "0")
570             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
571           (match_dup 1)
572           (const_int 1)))]
573   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
574   "<plusminus_mnemonic>s<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
575   [(set_attr "type" "sseadd")
576    (set_attr "mode" "<ssescalarmode>")])
577
578 (define_expand "mul<mode>3"
579   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "")
580         (mult:AVX256MODEF2P
581           (match_operand:AVX256MODEF2P 1 "nonimmediate_operand" "")
582           (match_operand:AVX256MODEF2P 2 "nonimmediate_operand" "")))]
583   "AVX256_VEC_FLOAT_MODE_P (<MODE>mode)"
584   "ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);")
585
586 (define_insn "*avx_mul<mode>3"
587   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
588         (mult:AVXMODEF2P
589           (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "%x")
590           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
591   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)
592    && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
593   "vmulp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
594   [(set_attr "type" "ssemul")
595    (set_attr "prefix" "vex")
596    (set_attr "mode" "<avxvecmode>")])
597
598 (define_expand "mul<mode>3"
599   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
600         (mult:SSEMODEF2P
601           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "")
602           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "")))]
603   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
604   "ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);")
605
606 (define_insn "*mul<mode>3"
607   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
608         (mult:SSEMODEF2P
609           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0")
610           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
611   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)
612    && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
613   "mulp<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
614   [(set_attr "type" "ssemul")
615    (set_attr "mode" "<MODE>")])
616
617 (define_insn "*avx_vmmul<mode>3"
618   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
619         (vec_merge:SSEMODEF2P
620           (mult:SSEMODEF2P
621             (match_operand:SSEMODEF2P 1 "register_operand" "x")
622             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
623           (match_dup 1)
624           (const_int 1)))]
625   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
626   "vmuls<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
627   [(set_attr "type" "ssemul")
628    (set_attr "prefix" "vex")
629    (set_attr "mode" "<ssescalarmode>")])
630
631 (define_insn "<sse>_vmmul<mode>3"
632   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
633         (vec_merge:SSEMODEF2P
634           (mult:SSEMODEF2P
635             (match_operand:SSEMODEF2P 1 "register_operand" "0")
636             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
637           (match_dup 1)
638           (const_int 1)))]
639   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
640   "muls<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
641   [(set_attr "type" "ssemul")
642    (set_attr "mode" "<ssescalarmode>")])
643
644 (define_expand "divv8sf3"
645   [(set (match_operand:V8SF 0 "register_operand" "")
646         (div:V8SF (match_operand:V8SF 1 "register_operand" "")
647                   (match_operand:V8SF 2 "nonimmediate_operand" "")))]
648   "TARGET_AVX"
649 {
650   ix86_fixup_binary_operands_no_copy (DIV, V8SFmode, operands);
651
652   if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
653       && flag_finite_math_only && !flag_trapping_math
654       && flag_unsafe_math_optimizations)
655     {
656       ix86_emit_swdivsf (operands[0], operands[1],
657                          operands[2], V8SFmode);
658       DONE;
659     }
660 })
661
662 (define_expand "divv4df3"
663   [(set (match_operand:V4DF 0 "register_operand" "")
664         (div:V4DF (match_operand:V4DF 1 "register_operand" "")
665                   (match_operand:V4DF 2 "nonimmediate_operand" "")))]
666   "TARGET_AVX"
667   "ix86_fixup_binary_operands_no_copy (DIV, V4DFmode, operands);")
668
669 (define_insn "avx_div<mode>3"
670   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
671         (div:AVXMODEF2P
672           (match_operand:AVXMODEF2P 1 "register_operand" "x")
673           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
674   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
675   "vdivp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
676   [(set_attr "type" "ssediv")
677    (set_attr "prefix" "vex")
678    (set_attr "mode" "<MODE>")])
679
680 (define_expand "divv4sf3"
681   [(set (match_operand:V4SF 0 "register_operand" "")
682         (div:V4SF (match_operand:V4SF 1 "register_operand" "")
683                   (match_operand:V4SF 2 "nonimmediate_operand" "")))]
684   "TARGET_SSE"
685 {
686   if (TARGET_SSE_MATH && TARGET_RECIP && optimize_insn_for_speed_p ()
687       && flag_finite_math_only && !flag_trapping_math
688       && flag_unsafe_math_optimizations)
689     {
690       ix86_emit_swdivsf (operands[0], operands[1],
691                          operands[2], V4SFmode);
692       DONE;
693     }
694 })
695
696 (define_expand "divv2df3"
697   [(set (match_operand:V2DF 0 "register_operand" "")
698         (div:V2DF (match_operand:V2DF 1 "register_operand" "")
699                   (match_operand:V2DF 2 "nonimmediate_operand" "")))]
700   "TARGET_SSE2"
701   "")
702
703 (define_insn "*avx_div<mode>3"
704   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
705         (div:SSEMODEF2P
706           (match_operand:SSEMODEF2P 1 "register_operand" "x")
707           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
708   "AVX128_VEC_FLOAT_MODE_P (<MODE>mode)"
709   "vdivp<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
710   [(set_attr "type" "ssediv")
711    (set_attr "prefix" "vex")
712    (set_attr "mode" "<MODE>")])
713
714 (define_insn "<sse>_div<mode>3"
715   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
716         (div:SSEMODEF2P
717           (match_operand:SSEMODEF2P 1 "register_operand" "0")
718           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
719   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
720   "divp<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
721   [(set_attr "type" "ssediv")
722    (set_attr "mode" "<MODE>")])
723
724 (define_insn "*avx_vmdiv<mode>3"
725   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
726         (vec_merge:SSEMODEF2P
727           (div:SSEMODEF2P
728             (match_operand:SSEMODEF2P 1 "register_operand" "x")
729             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
730           (match_dup 1)
731           (const_int 1)))]
732   "AVX128_VEC_FLOAT_MODE_P (<MODE>mode)"
733   "vdivs<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
734   [(set_attr "type" "ssediv")
735    (set_attr "prefix" "vex")
736    (set_attr "mode" "<ssescalarmode>")])
737
738 (define_insn "<sse>_vmdiv<mode>3"
739   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
740         (vec_merge:SSEMODEF2P
741           (div:SSEMODEF2P
742             (match_operand:SSEMODEF2P 1 "register_operand" "0")
743             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
744           (match_dup 1)
745           (const_int 1)))]
746   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
747   "divs<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
748   [(set_attr "type" "ssediv")
749    (set_attr "mode" "<ssescalarmode>")])
750
751 (define_insn "avx_rcpv8sf2"
752   [(set (match_operand:V8SF 0 "register_operand" "=x")
753         (unspec:V8SF
754           [(match_operand:V8SF 1 "nonimmediate_operand" "xm")] UNSPEC_RCP))]
755   "TARGET_AVX"
756   "vrcpps\t{%1, %0|%0, %1}"
757   [(set_attr "type" "sse")
758    (set_attr "prefix" "vex")
759    (set_attr "mode" "V8SF")])
760
761 (define_insn "sse_rcpv4sf2"
762   [(set (match_operand:V4SF 0 "register_operand" "=x")
763         (unspec:V4SF
764           [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_RCP))]
765   "TARGET_SSE"
766   "%vrcpps\t{%1, %0|%0, %1}"
767   [(set_attr "type" "sse")
768    (set_attr "prefix" "maybe_vex")
769    (set_attr "mode" "V4SF")])
770
771 (define_insn "*avx_vmrcpv4sf2"
772   [(set (match_operand:V4SF 0 "register_operand" "=x")
773         (vec_merge:V4SF
774           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
775                        UNSPEC_RCP)
776           (match_operand:V4SF 2 "register_operand" "x")
777           (const_int 1)))]
778   "TARGET_AVX"
779   "vrcpss\t{%1, %2, %0|%0, %2, %1}"
780   [(set_attr "type" "sse")
781    (set_attr "prefix" "vex")
782    (set_attr "mode" "SF")])
783
784 (define_insn "sse_vmrcpv4sf2"
785   [(set (match_operand:V4SF 0 "register_operand" "=x")
786         (vec_merge:V4SF
787           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
788                        UNSPEC_RCP)
789           (match_operand:V4SF 2 "register_operand" "0")
790           (const_int 1)))]
791   "TARGET_SSE"
792   "rcpss\t{%1, %0|%0, %1}"
793   [(set_attr "type" "sse")
794    (set_attr "mode" "SF")])
795
796 (define_expand "sqrtv8sf2"
797   [(set (match_operand:V8SF 0 "register_operand" "")
798         (sqrt:V8SF (match_operand:V8SF 1 "nonimmediate_operand" "")))]
799   "TARGET_AVX"
800 {
801   if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
802       && flag_finite_math_only && !flag_trapping_math
803       && flag_unsafe_math_optimizations)
804     {
805       ix86_emit_swsqrtsf (operands[0], operands[1], V8SFmode, 0);
806       DONE;
807     }
808 })
809
810 (define_insn "avx_sqrtv8sf2"
811   [(set (match_operand:V8SF 0 "register_operand" "=x")
812         (sqrt:V8SF (match_operand:V8SF 1 "nonimmediate_operand" "xm")))]
813   "TARGET_AVX"
814   "vsqrtps\t{%1, %0|%0, %1}"
815   [(set_attr "type" "sse")
816    (set_attr "prefix" "vex")
817    (set_attr "mode" "V8SF")])
818
819 (define_expand "sqrtv4sf2"
820   [(set (match_operand:V4SF 0 "register_operand" "")
821         (sqrt:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "")))]
822   "TARGET_SSE"
823 {
824   if (TARGET_SSE_MATH && TARGET_RECIP && optimize_insn_for_speed_p ()
825       && flag_finite_math_only && !flag_trapping_math
826       && flag_unsafe_math_optimizations)
827     {
828       ix86_emit_swsqrtsf (operands[0], operands[1], V4SFmode, 0);
829       DONE;
830     }
831 })
832
833 (define_insn "sse_sqrtv4sf2"
834   [(set (match_operand:V4SF 0 "register_operand" "=x")
835         (sqrt:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
836   "TARGET_SSE"
837   "%vsqrtps\t{%1, %0|%0, %1}"
838   [(set_attr "type" "sse")
839    (set_attr "prefix" "maybe_vex")
840    (set_attr "mode" "V4SF")])
841
842 (define_insn "sqrtv4df2"
843   [(set (match_operand:V4DF 0 "register_operand" "=x")
844         (sqrt:V4DF (match_operand:V4DF 1 "nonimmediate_operand" "xm")))]
845   "TARGET_AVX"
846   "vsqrtpd\t{%1, %0|%0, %1}"
847   [(set_attr "type" "sse")
848    (set_attr "prefix" "vex")
849    (set_attr "mode" "V4DF")])
850
851 (define_insn "sqrtv2df2"
852   [(set (match_operand:V2DF 0 "register_operand" "=x")
853         (sqrt:V2DF (match_operand:V2DF 1 "nonimmediate_operand" "xm")))]
854   "TARGET_SSE2"
855   "%vsqrtpd\t{%1, %0|%0, %1}"
856   [(set_attr "type" "sse")
857    (set_attr "prefix" "maybe_vex")
858    (set_attr "mode" "V2DF")])
859
860 (define_insn "*avx_vmsqrt<mode>2"
861   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
862         (vec_merge:SSEMODEF2P
863           (sqrt:SSEMODEF2P
864             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "xm"))
865           (match_operand:SSEMODEF2P 2 "register_operand" "x")
866           (const_int 1)))]
867   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
868   "vsqrts<ssemodesuffixf2c>\t{%1, %2, %0|%0, %2, %1}"
869   [(set_attr "type" "sse")
870    (set_attr "prefix" "vex")
871    (set_attr "mode" "<ssescalarmode>")])
872
873 (define_insn "<sse>_vmsqrt<mode>2"
874   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
875         (vec_merge:SSEMODEF2P
876           (sqrt:SSEMODEF2P
877             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "xm"))
878           (match_operand:SSEMODEF2P 2 "register_operand" "0")
879           (const_int 1)))]
880   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
881   "sqrts<ssemodesuffixf2c>\t{%1, %0|%0, %1}"
882   [(set_attr "type" "sse")
883    (set_attr "mode" "<ssescalarmode>")])
884
885 (define_expand "rsqrtv8sf2"
886   [(set (match_operand:V8SF 0 "register_operand" "")
887         (unspec:V8SF
888           [(match_operand:V8SF 1 "nonimmediate_operand" "")] UNSPEC_RSQRT))]
889   "TARGET_AVX && TARGET_SSE_MATH"
890 {
891   ix86_emit_swsqrtsf (operands[0], operands[1], V8SFmode, 1);
892   DONE;
893 })
894
895 (define_insn "avx_rsqrtv8sf2"
896   [(set (match_operand:V8SF 0 "register_operand" "=x")
897         (unspec:V8SF
898           [(match_operand:V8SF 1 "nonimmediate_operand" "xm")] UNSPEC_RSQRT))]
899   "TARGET_AVX"
900   "vrsqrtps\t{%1, %0|%0, %1}"
901   [(set_attr "type" "sse")
902    (set_attr "prefix" "vex")
903    (set_attr "mode" "V8SF")])
904
905 (define_expand "rsqrtv4sf2"
906   [(set (match_operand:V4SF 0 "register_operand" "")
907         (unspec:V4SF
908           [(match_operand:V4SF 1 "nonimmediate_operand" "")] UNSPEC_RSQRT))]
909   "TARGET_SSE_MATH"
910 {
911   ix86_emit_swsqrtsf (operands[0], operands[1], V4SFmode, 1);
912   DONE;
913 })
914
915 (define_insn "sse_rsqrtv4sf2"
916   [(set (match_operand:V4SF 0 "register_operand" "=x")
917         (unspec:V4SF
918           [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_RSQRT))]
919   "TARGET_SSE"
920   "%vrsqrtps\t{%1, %0|%0, %1}"
921   [(set_attr "type" "sse")
922    (set_attr "prefix" "maybe_vex")
923    (set_attr "mode" "V4SF")])
924
925 (define_insn "*avx_vmrsqrtv4sf2"
926   [(set (match_operand:V4SF 0 "register_operand" "=x")
927         (vec_merge:V4SF
928           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
929                        UNSPEC_RSQRT)
930           (match_operand:V4SF 2 "register_operand" "x")
931           (const_int 1)))]
932   "TARGET_AVX"
933   "vrsqrtss\t{%1, %2, %0|%0, %2, %1}"
934   [(set_attr "type" "sse")
935    (set_attr "prefix" "vex")
936    (set_attr "mode" "SF")])
937
938 (define_insn "sse_vmrsqrtv4sf2"
939   [(set (match_operand:V4SF 0 "register_operand" "=x")
940         (vec_merge:V4SF
941           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
942                        UNSPEC_RSQRT)
943           (match_operand:V4SF 2 "register_operand" "0")
944           (const_int 1)))]
945   "TARGET_SSE"
946   "rsqrtss\t{%1, %0|%0, %1}"
947   [(set_attr "type" "sse")
948    (set_attr "mode" "SF")])
949
950 ;; ??? For !flag_finite_math_only, the representation with SMIN/SMAX
951 ;; isn't really correct, as those rtl operators aren't defined when
952 ;; applied to NaNs.  Hopefully the optimizers won't get too smart on us.
953
954 (define_expand "<code><mode>3"
955   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "")
956         (smaxmin:AVX256MODEF2P
957           (match_operand:AVX256MODEF2P 1 "nonimmediate_operand" "")
958           (match_operand:AVX256MODEF2P 2 "nonimmediate_operand" "")))]
959   "AVX256_VEC_FLOAT_MODE_P (<MODE>mode)"
960 {
961   if (!flag_finite_math_only)
962     operands[1] = force_reg (<MODE>mode, operands[1]);
963   ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);
964 })
965
966 (define_expand "<code><mode>3"
967   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
968         (smaxmin:SSEMODEF2P
969           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "")
970           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "")))]
971   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
972 {
973   if (!flag_finite_math_only)
974     operands[1] = force_reg (<MODE>mode, operands[1]);
975   ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);
976 })
977
978 (define_insn "*avx_<code><mode>3_finite"
979   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
980         (smaxmin:AVXMODEF2P
981           (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "%x")
982           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
983   "AVX_VEC_FLOAT_MODE_P (<MODE>mode) && flag_finite_math_only
984    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
985   "v<maxminfprefix>p<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
986   [(set_attr "type" "sseadd")
987    (set_attr "prefix" "vex")
988    (set_attr "mode" "<MODE>")])
989
990 (define_insn "*<code><mode>3_finite"
991   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
992         (smaxmin:SSEMODEF2P
993           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0")
994           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
995   "SSE_VEC_FLOAT_MODE_P (<MODE>mode) && flag_finite_math_only
996    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
997   "<maxminfprefix>p<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
998   [(set_attr "type" "sseadd")
999    (set_attr "mode" "<MODE>")])
1000
1001 (define_insn "*avx_<code><mode>3"
1002   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1003         (smaxmin:AVXMODEF2P
1004           (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "%x")
1005           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
1006   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
1007   "v<maxminfprefix>p<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1008   [(set_attr "type" "sseadd")
1009    (set_attr "prefix" "vex")
1010    (set_attr "mode" "<avxvecmode>")])
1011
1012 (define_insn "*<code><mode>3"
1013   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1014         (smaxmin:SSEMODEF2P
1015           (match_operand:SSEMODEF2P 1 "register_operand" "0")
1016           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
1017   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1018   "<maxminfprefix>p<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1019   [(set_attr "type" "sseadd")
1020    (set_attr "mode" "<MODE>")])
1021
1022 (define_insn "*avx_vm<code><mode>3"
1023   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1024         (vec_merge:SSEMODEF2P
1025           (smaxmin:SSEMODEF2P
1026             (match_operand:SSEMODEF2P 1 "register_operand" "x")
1027             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
1028          (match_dup 1)
1029          (const_int 1)))]
1030   "AVX128_VEC_FLOAT_MODE_P (<MODE>mode)"
1031   "v<maxminfprefix>s<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1032   [(set_attr "type" "sse")
1033    (set_attr "prefix" "vex")
1034    (set_attr "mode" "<ssescalarmode>")])
1035
1036 (define_insn "<sse>_vm<code><mode>3"
1037   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1038         (vec_merge:SSEMODEF2P
1039           (smaxmin:SSEMODEF2P
1040             (match_operand:SSEMODEF2P 1 "register_operand" "0")
1041             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm"))
1042          (match_dup 1)
1043          (const_int 1)))]
1044   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1045   "<maxminfprefix>s<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1046   [(set_attr "type" "sse")
1047    (set_attr "mode" "<ssescalarmode>")])
1048
1049 ;; These versions of the min/max patterns implement exactly the operations
1050 ;;   min = (op1 < op2 ? op1 : op2)
1051 ;;   max = (!(op1 < op2) ? op1 : op2)
1052 ;; Their operands are not commutative, and thus they may be used in the
1053 ;; presence of -0.0 and NaN.
1054
1055 (define_insn "*avx_ieee_smin<mode>3"
1056   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1057         (unspec:AVXMODEF2P
1058           [(match_operand:AVXMODEF2P 1 "register_operand" "x")
1059            (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")]
1060          UNSPEC_IEEE_MIN))]
1061   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
1062   "vminp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1063   [(set_attr "type" "sseadd")
1064    (set_attr "prefix" "vex")
1065    (set_attr "mode" "<avxvecmode>")])
1066
1067 (define_insn "*avx_ieee_smax<mode>3"
1068   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1069         (unspec:AVXMODEF2P
1070           [(match_operand:AVXMODEF2P 1 "register_operand" "x")
1071            (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")]
1072          UNSPEC_IEEE_MAX))]
1073   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
1074   "vmaxp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1075   [(set_attr "type" "sseadd")
1076    (set_attr "prefix" "vex")
1077    (set_attr "mode" "<avxvecmode>")])
1078
1079 (define_insn "*ieee_smin<mode>3"
1080   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1081         (unspec:SSEMODEF2P
1082           [(match_operand:SSEMODEF2P 1 "register_operand" "0")
1083            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")]
1084          UNSPEC_IEEE_MIN))]
1085   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1086   "minp<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1087   [(set_attr "type" "sseadd")
1088    (set_attr "mode" "<MODE>")])
1089
1090 (define_insn "*ieee_smax<mode>3"
1091   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1092         (unspec:SSEMODEF2P
1093           [(match_operand:SSEMODEF2P 1 "register_operand" "0")
1094            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")]
1095          UNSPEC_IEEE_MAX))]
1096   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1097   "maxp<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1098   [(set_attr "type" "sseadd")
1099    (set_attr "mode" "<MODE>")])
1100
1101 (define_insn "avx_addsubv8sf3"
1102   [(set (match_operand:V8SF 0 "register_operand" "=x")
1103         (vec_merge:V8SF
1104           (plus:V8SF
1105             (match_operand:V8SF 1 "register_operand" "x")
1106             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
1107           (minus:V8SF (match_dup 1) (match_dup 2))
1108           (const_int 170)))]
1109   "TARGET_AVX"
1110   "vaddsubps\t{%2, %1, %0|%0, %1, %2}"
1111   [(set_attr "type" "sseadd")
1112    (set_attr "prefix" "vex")
1113    (set_attr "mode" "V8SF")])
1114
1115 (define_insn "avx_addsubv4df3"
1116   [(set (match_operand:V4DF 0 "register_operand" "=x")
1117         (vec_merge:V4DF
1118           (plus:V4DF
1119             (match_operand:V4DF 1 "register_operand" "x")
1120             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
1121           (minus:V4DF (match_dup 1) (match_dup 2))
1122           (const_int 10)))]
1123   "TARGET_AVX"
1124   "vaddsubpd\t{%2, %1, %0|%0, %1, %2}"
1125   [(set_attr "type" "sseadd")
1126    (set_attr "prefix" "vex")
1127    (set_attr "mode" "V4DF")])
1128
1129 (define_insn "*avx_addsubv4sf3"
1130   [(set (match_operand:V4SF 0 "register_operand" "=x")
1131         (vec_merge:V4SF
1132           (plus:V4SF
1133             (match_operand:V4SF 1 "register_operand" "x")
1134             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
1135           (minus:V4SF (match_dup 1) (match_dup 2))
1136           (const_int 10)))]
1137   "TARGET_AVX"
1138   "vaddsubps\t{%2, %1, %0|%0, %1, %2}"
1139   [(set_attr "type" "sseadd")
1140    (set_attr "prefix" "vex")
1141    (set_attr "mode" "V4SF")])
1142
1143 (define_insn "sse3_addsubv4sf3"
1144   [(set (match_operand:V4SF 0 "register_operand" "=x")
1145         (vec_merge:V4SF
1146           (plus:V4SF
1147             (match_operand:V4SF 1 "register_operand" "0")
1148             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
1149           (minus:V4SF (match_dup 1) (match_dup 2))
1150           (const_int 10)))]
1151   "TARGET_SSE3"
1152   "addsubps\t{%2, %0|%0, %2}"
1153   [(set_attr "type" "sseadd")
1154    (set_attr "prefix_rep" "1")
1155    (set_attr "mode" "V4SF")])
1156
1157 (define_insn "*avx_addsubv2df3"
1158   [(set (match_operand:V2DF 0 "register_operand" "=x")
1159         (vec_merge:V2DF
1160           (plus:V2DF
1161             (match_operand:V2DF 1 "register_operand" "x")
1162             (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
1163           (minus:V2DF (match_dup 1) (match_dup 2))
1164           (const_int 2)))]
1165   "TARGET_AVX"
1166   "vaddsubpd\t{%2, %1, %0|%0, %1, %2}"
1167   [(set_attr "type" "sseadd")
1168    (set_attr "prefix" "vex")
1169    (set_attr "mode" "V2DF")])
1170
1171 (define_insn "sse3_addsubv2df3"
1172   [(set (match_operand:V2DF 0 "register_operand" "=x")
1173         (vec_merge:V2DF
1174           (plus:V2DF
1175             (match_operand:V2DF 1 "register_operand" "0")
1176             (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
1177           (minus:V2DF (match_dup 1) (match_dup 2))
1178           (const_int 2)))]
1179   "TARGET_SSE3"
1180   "addsubpd\t{%2, %0|%0, %2}"
1181   [(set_attr "type" "sseadd")
1182    (set_attr "mode" "V2DF")])
1183
1184 (define_insn "avx_h<plusminus_insn>v4df3"
1185   [(set (match_operand:V4DF 0 "register_operand" "=x")
1186         (vec_concat:V4DF
1187           (vec_concat:V2DF
1188             (plusminus:DF
1189               (vec_select:DF
1190                 (match_operand:V4DF 1 "register_operand" "x")
1191                 (parallel [(const_int 0)]))
1192               (vec_select:DF (match_dup 1) (parallel [(const_int 1)])))
1193             (plusminus:DF
1194               (vec_select:DF (match_dup 1) (parallel [(const_int 2)]))
1195               (vec_select:DF (match_dup 1) (parallel [(const_int 3)]))))
1196           (vec_concat:V2DF
1197             (plusminus:DF
1198               (vec_select:DF
1199                 (match_operand:V4DF 2 "nonimmediate_operand" "xm")
1200                 (parallel [(const_int 0)]))
1201               (vec_select:DF (match_dup 2) (parallel [(const_int 1)])))
1202             (plusminus:DF
1203               (vec_select:DF (match_dup 2) (parallel [(const_int 2)]))
1204               (vec_select:DF (match_dup 2) (parallel [(const_int 3)]))))))]
1205   "TARGET_AVX"
1206   "vh<plusminus_mnemonic>pd\t{%2, %1, %0|%0, %1, %2}"
1207   [(set_attr "type" "sseadd")
1208    (set_attr "prefix" "vex")
1209    (set_attr "mode" "V4DF")])
1210
1211 (define_insn "avx_h<plusminus_insn>v8sf3"
1212   [(set (match_operand:V8SF 0 "register_operand" "=x")
1213         (vec_concat:V8SF
1214           (vec_concat:V4SF
1215             (vec_concat:V2SF
1216               (plusminus:SF
1217                 (vec_select:SF
1218                   (match_operand:V8SF 1 "register_operand" "x")
1219                   (parallel [(const_int 0)]))
1220                 (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
1221               (plusminus:SF
1222                 (vec_select:SF (match_dup 1) (parallel [(const_int 2)]))
1223                 (vec_select:SF (match_dup 1) (parallel [(const_int 3)]))))
1224             (vec_concat:V2SF
1225               (plusminus:SF
1226                 (vec_select:SF
1227                   (match_operand:V8SF 2 "nonimmediate_operand" "xm")
1228                   (parallel [(const_int 0)]))
1229                 (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))
1230               (plusminus:SF
1231                 (vec_select:SF (match_dup 2) (parallel [(const_int 2)]))
1232                 (vec_select:SF (match_dup 2) (parallel [(const_int 3)])))))
1233           (vec_concat:V4SF
1234             (vec_concat:V2SF
1235               (plusminus:SF
1236                 (vec_select:SF (match_dup 1) (parallel [(const_int 4)]))
1237                 (vec_select:SF (match_dup 1) (parallel [(const_int 5)])))
1238               (plusminus:SF
1239                 (vec_select:SF (match_dup 1) (parallel [(const_int 6)]))
1240                 (vec_select:SF (match_dup 1) (parallel [(const_int 7)]))))
1241             (vec_concat:V2SF
1242               (plusminus:SF
1243                 (vec_select:SF (match_dup 2) (parallel [(const_int 4)]))
1244                 (vec_select:SF (match_dup 2) (parallel [(const_int 5)])))
1245               (plusminus:SF
1246                 (vec_select:SF (match_dup 2) (parallel [(const_int 6)]))
1247                 (vec_select:SF (match_dup 2) (parallel [(const_int 7)])))))))]
1248   "TARGET_AVX"
1249   "vh<plusminus_mnemonic>ps\t{%2, %1, %0|%0, %1, %2}"
1250   [(set_attr "type" "sseadd")
1251    (set_attr "prefix" "vex")
1252    (set_attr "mode" "V8SF")])
1253
1254 (define_insn "*avx_h<plusminus_insn>v4sf3"
1255   [(set (match_operand:V4SF 0 "register_operand" "=x")
1256         (vec_concat:V4SF
1257           (vec_concat:V2SF
1258             (plusminus:SF
1259               (vec_select:SF
1260                 (match_operand:V4SF 1 "register_operand" "x")
1261                 (parallel [(const_int 0)]))
1262               (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
1263             (plusminus:SF
1264               (vec_select:SF (match_dup 1) (parallel [(const_int 2)]))
1265               (vec_select:SF (match_dup 1) (parallel [(const_int 3)]))))
1266           (vec_concat:V2SF
1267             (plusminus:SF
1268               (vec_select:SF
1269                 (match_operand:V4SF 2 "nonimmediate_operand" "xm")
1270                 (parallel [(const_int 0)]))
1271               (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))
1272             (plusminus:SF
1273               (vec_select:SF (match_dup 2) (parallel [(const_int 2)]))
1274               (vec_select:SF (match_dup 2) (parallel [(const_int 3)]))))))]
1275   "TARGET_AVX"
1276   "vh<plusminus_mnemonic>ps\t{%2, %1, %0|%0, %1, %2}"
1277   [(set_attr "type" "sseadd")
1278    (set_attr "prefix" "vex")
1279    (set_attr "mode" "V4SF")])
1280
1281 (define_insn "sse3_h<plusminus_insn>v4sf3"
1282   [(set (match_operand:V4SF 0 "register_operand" "=x")
1283         (vec_concat:V4SF
1284           (vec_concat:V2SF
1285             (plusminus:SF
1286               (vec_select:SF
1287                 (match_operand:V4SF 1 "register_operand" "0")
1288                 (parallel [(const_int 0)]))
1289               (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
1290             (plusminus:SF
1291               (vec_select:SF (match_dup 1) (parallel [(const_int 2)]))
1292               (vec_select:SF (match_dup 1) (parallel [(const_int 3)]))))
1293           (vec_concat:V2SF
1294             (plusminus:SF
1295               (vec_select:SF
1296                 (match_operand:V4SF 2 "nonimmediate_operand" "xm")
1297                 (parallel [(const_int 0)]))
1298               (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))
1299             (plusminus:SF
1300               (vec_select:SF (match_dup 2) (parallel [(const_int 2)]))
1301               (vec_select:SF (match_dup 2) (parallel [(const_int 3)]))))))]
1302   "TARGET_SSE3"
1303   "h<plusminus_mnemonic>ps\t{%2, %0|%0, %2}"
1304   [(set_attr "type" "sseadd")
1305    (set_attr "prefix_rep" "1")
1306    (set_attr "mode" "V4SF")])
1307
1308 (define_insn "*avx_h<plusminus_insn>v2df3"
1309   [(set (match_operand:V2DF 0 "register_operand" "=x")
1310         (vec_concat:V2DF
1311           (plusminus:DF
1312             (vec_select:DF
1313               (match_operand:V2DF 1 "register_operand" "x")
1314               (parallel [(const_int 0)]))
1315             (vec_select:DF (match_dup 1) (parallel [(const_int 1)])))
1316           (plusminus:DF
1317             (vec_select:DF
1318               (match_operand:V2DF 2 "nonimmediate_operand" "xm")
1319               (parallel [(const_int 0)]))
1320             (vec_select:DF (match_dup 2) (parallel [(const_int 1)])))))]
1321   "TARGET_AVX"
1322   "vh<plusminus_mnemonic>pd\t{%2, %1, %0|%0, %1, %2}"
1323   [(set_attr "type" "sseadd")
1324    (set_attr "prefix" "vex")
1325    (set_attr "mode" "V2DF")])
1326
1327 (define_insn "sse3_h<plusminus_insn>v2df3"
1328   [(set (match_operand:V2DF 0 "register_operand" "=x")
1329         (vec_concat:V2DF
1330           (plusminus:DF
1331             (vec_select:DF
1332               (match_operand:V2DF 1 "register_operand" "0")
1333               (parallel [(const_int 0)]))
1334             (vec_select:DF (match_dup 1) (parallel [(const_int 1)])))
1335           (plusminus:DF
1336             (vec_select:DF
1337               (match_operand:V2DF 2 "nonimmediate_operand" "xm")
1338               (parallel [(const_int 0)]))
1339             (vec_select:DF (match_dup 2) (parallel [(const_int 1)])))))]
1340   "TARGET_SSE3"
1341   "h<plusminus_mnemonic>pd\t{%2, %0|%0, %2}"
1342   [(set_attr "type" "sseadd")
1343    (set_attr "mode" "V2DF")])
1344
1345 (define_expand "reduc_splus_v4sf"
1346   [(match_operand:V4SF 0 "register_operand" "")
1347    (match_operand:V4SF 1 "register_operand" "")]
1348   "TARGET_SSE"
1349 {
1350   if (TARGET_SSE3)
1351     {
1352       rtx tmp = gen_reg_rtx (V4SFmode);
1353       emit_insn (gen_sse3_haddv4sf3 (tmp, operands[1], operands[1]));
1354       emit_insn (gen_sse3_haddv4sf3 (operands[0], tmp, tmp));
1355     }
1356   else
1357     ix86_expand_reduc_v4sf (gen_addv4sf3, operands[0], operands[1]);
1358   DONE;
1359 })
1360
1361 (define_expand "reduc_splus_v2df"
1362   [(match_operand:V2DF 0 "register_operand" "")
1363    (match_operand:V2DF 1 "register_operand" "")]
1364   "TARGET_SSE3"
1365 {
1366   emit_insn (gen_sse3_haddv2df3 (operands[0], operands[1], operands[1]));
1367   DONE;
1368 })
1369
1370 (define_expand "reduc_smax_v4sf"
1371   [(match_operand:V4SF 0 "register_operand" "")
1372    (match_operand:V4SF 1 "register_operand" "")]
1373   "TARGET_SSE"
1374 {
1375   ix86_expand_reduc_v4sf (gen_smaxv4sf3, operands[0], operands[1]);
1376   DONE;
1377 })
1378
1379 (define_expand "reduc_smin_v4sf"
1380   [(match_operand:V4SF 0 "register_operand" "")
1381    (match_operand:V4SF 1 "register_operand" "")]
1382   "TARGET_SSE"
1383 {
1384   ix86_expand_reduc_v4sf (gen_sminv4sf3, operands[0], operands[1]);
1385   DONE;
1386 })
1387
1388 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1389 ;;
1390 ;; Parallel floating point comparisons
1391 ;;
1392 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1393
1394 (define_insn "avx_cmpp<avxmodesuffixf2c><mode>3"
1395   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1396         (unspec:AVXMODEF2P
1397           [(match_operand:AVXMODEF2P 1 "register_operand" "x")
1398            (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")
1399            (match_operand:SI 3 "const_0_to_31_operand" "n")]
1400           UNSPEC_PCMP))]
1401   "TARGET_AVX"
1402   "vcmpp<avxmodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1403   [(set_attr "type" "ssecmp")
1404    (set_attr "prefix" "vex")
1405    (set_attr "mode" "<MODE>")])
1406
1407 (define_insn "avx_cmps<ssemodesuffixf2c><mode>3"
1408   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1409         (vec_merge:SSEMODEF2P
1410           (unspec:SSEMODEF2P
1411             [(match_operand:SSEMODEF2P 1 "register_operand" "x")
1412              (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")
1413              (match_operand:SI 3 "const_0_to_31_operand" "n")]
1414             UNSPEC_PCMP)
1415          (match_dup 1)
1416          (const_int 1)))]
1417   "TARGET_AVX"
1418   "vcmps<ssemodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1419   [(set_attr "type" "ssecmp")
1420    (set_attr "prefix" "vex")
1421    (set_attr "mode" "<ssescalarmode>")])
1422
1423 ;; We don't promote 128bit vector compare intrinsics. But vectorizer
1424 ;; may generate 256bit vector compare instructions.
1425 (define_insn "*avx_maskcmp<mode>3"
1426   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1427         (match_operator:AVXMODEF2P 3 "avx_comparison_float_operator"
1428                 [(match_operand:AVXMODEF2P 1 "register_operand" "x")
1429                  (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")]))]
1430   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
1431   "vcmp%D3p<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1432   [(set_attr "type" "ssecmp")
1433    (set_attr "prefix" "vex")
1434    (set_attr "mode" "<avxvecmode>")])
1435
1436 (define_insn "<sse>_maskcmp<mode>3"
1437   [(set (match_operand:SSEMODEF4 0 "register_operand" "=x")
1438         (match_operator:SSEMODEF4 3 "sse_comparison_operator"
1439                 [(match_operand:SSEMODEF4 1 "register_operand" "0")
1440                  (match_operand:SSEMODEF4 2 "nonimmediate_operand" "xm")]))]
1441   "(SSE_FLOAT_MODE_P (<MODE>mode) || SSE_VEC_FLOAT_MODE_P (<MODE>mode))
1442    && !TARGET_SSE5"
1443   "cmp%D3<ssemodesuffixf4>\t{%2, %0|%0, %2}"
1444   [(set_attr "type" "ssecmp")
1445    (set_attr "mode" "<MODE>")])
1446
1447 (define_insn "<sse>_vmmaskcmp<mode>3"
1448   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1449         (vec_merge:SSEMODEF2P
1450          (match_operator:SSEMODEF2P 3 "sse_comparison_operator"
1451                 [(match_operand:SSEMODEF2P 1 "register_operand" "0")
1452                  (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")])
1453          (match_dup 1)
1454          (const_int 1)))]
1455   "SSE_VEC_FLOAT_MODE_P (<MODE>mode) && !TARGET_SSE5"
1456   "cmp%D3s<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1457   [(set_attr "type" "ssecmp")
1458    (set_attr "mode" "<ssescalarmode>")])
1459
1460 (define_insn "<sse>_comi"
1461   [(set (reg:CCFP FLAGS_REG)
1462         (compare:CCFP
1463           (vec_select:MODEF
1464             (match_operand:<ssevecmode> 0 "register_operand" "x")
1465             (parallel [(const_int 0)]))
1466           (vec_select:MODEF
1467             (match_operand:<ssevecmode> 1 "nonimmediate_operand" "xm")
1468             (parallel [(const_int 0)]))))]
1469   "SSE_FLOAT_MODE_P (<MODE>mode)"
1470   "%vcomis<ssemodefsuffix>\t{%1, %0|%0, %1}"
1471   [(set_attr "type" "ssecomi")
1472    (set_attr "prefix" "maybe_vex")
1473    (set_attr "mode" "<MODE>")])
1474
1475 (define_insn "<sse>_ucomi"
1476   [(set (reg:CCFPU FLAGS_REG)
1477         (compare:CCFPU
1478           (vec_select:MODEF
1479             (match_operand:<ssevecmode> 0 "register_operand" "x")
1480             (parallel [(const_int 0)]))
1481           (vec_select:MODEF
1482             (match_operand:<ssevecmode> 1 "nonimmediate_operand" "xm")
1483             (parallel [(const_int 0)]))))]
1484   "SSE_FLOAT_MODE_P (<MODE>mode)"
1485   "%vucomis<ssemodefsuffix>\t{%1, %0|%0, %1}"
1486   [(set_attr "type" "ssecomi")
1487    (set_attr "prefix" "maybe_vex")
1488    (set_attr "mode" "<MODE>")])
1489
1490 (define_expand "vcond<mode>"
1491   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1492         (if_then_else:SSEMODEF2P
1493           (match_operator 3 ""
1494             [(match_operand:SSEMODEF2P 4 "nonimmediate_operand" "")
1495              (match_operand:SSEMODEF2P 5 "nonimmediate_operand" "")])
1496           (match_operand:SSEMODEF2P 1 "general_operand" "")
1497           (match_operand:SSEMODEF2P 2 "general_operand" "")))]
1498   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1499 {
1500   bool ok = ix86_expand_fp_vcond (operands);
1501   gcc_assert (ok);
1502   DONE;
1503 })
1504
1505 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1506 ;;
1507 ;; Parallel floating point logical operations
1508 ;;
1509 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1510
1511 (define_insn "avx_andnot<mode>3"
1512   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1513         (and:AVXMODEF2P
1514           (not:AVXMODEF2P
1515             (match_operand:AVXMODEF2P 1 "register_operand" "x"))
1516           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
1517   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)"
1518   "vandnp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1519   [(set_attr "type" "sselog")
1520    (set_attr "prefix" "vex")
1521    (set_attr "mode" "<avxvecmode>")])
1522
1523 (define_insn "<sse>_andnot<mode>3"
1524   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1525         (and:SSEMODEF2P
1526           (not:SSEMODEF2P
1527             (match_operand:SSEMODEF2P 1 "register_operand" "0"))
1528           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
1529   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1530   "andnp<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1531   [(set_attr "type" "sselog")
1532    (set_attr "mode" "<MODE>")])
1533
1534 (define_expand "<code><mode>3"
1535   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "")
1536         (plogic:AVX256MODEF2P
1537           (match_operand:AVX256MODEF2P 1 "nonimmediate_operand" "")
1538           (match_operand:AVX256MODEF2P 2 "nonimmediate_operand" "")))]
1539   "AVX256_VEC_FLOAT_MODE_P (<MODE>mode)"
1540   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
1541
1542 (define_insn "*avx_<code><mode>3"
1543   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
1544         (plogic:AVXMODEF2P
1545           (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "%x")
1546           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")))]
1547   "AVX_VEC_FLOAT_MODE_P (<MODE>mode)
1548    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
1549   "v<plogicprefix>p<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
1550   [(set_attr "type" "sselog")
1551    (set_attr "prefix" "vex")
1552    (set_attr "mode" "<avxvecmode>")])
1553
1554 (define_expand "<code><mode>3"
1555   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1556         (plogic:SSEMODEF2P
1557           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "")
1558           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "")))]
1559   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
1560   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
1561
1562 (define_insn "*<code><mode>3"
1563   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
1564         (plogic:SSEMODEF2P
1565           (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0")
1566           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")))]
1567   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)
1568    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
1569   "<plogicprefix>p<ssemodesuffixf2c>\t{%2, %0|%0, %2}"
1570   [(set_attr "type" "sselog")
1571    (set_attr "mode" "<MODE>")])
1572
1573 ;; Also define scalar versions.  These are used for abs, neg, and
1574 ;; conditional move.  Using subregs into vector modes causes register
1575 ;; allocation lossage.  These patterns do not allow memory operands
1576 ;; because the native instructions read the full 128-bits.
1577
1578 (define_insn "*avx_andnot<mode>3"
1579   [(set (match_operand:MODEF 0 "register_operand" "=x")
1580         (and:MODEF
1581           (not:MODEF
1582             (match_operand:MODEF 1 "register_operand" "x"))
1583             (match_operand:MODEF 2 "register_operand" "x")))]
1584   "AVX_FLOAT_MODE_P (<MODE>mode)"
1585   "vandnp<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
1586   [(set_attr "type" "sselog")
1587    (set_attr "prefix" "vex")
1588    (set_attr "mode" "<ssevecmode>")])
1589
1590 (define_insn "*andnot<mode>3"
1591   [(set (match_operand:MODEF 0 "register_operand" "=x")
1592         (and:MODEF
1593           (not:MODEF
1594             (match_operand:MODEF 1 "register_operand" "0"))
1595             (match_operand:MODEF 2 "register_operand" "x")))]
1596   "SSE_FLOAT_MODE_P (<MODE>mode)"
1597   "andnp<ssemodefsuffix>\t{%2, %0|%0, %2}"
1598   [(set_attr "type" "sselog")
1599    (set_attr "mode" "<ssevecmode>")])
1600
1601 (define_insn "*avx_<code><mode>3"
1602   [(set (match_operand:MODEF 0 "register_operand" "=x")
1603         (plogic:MODEF
1604           (match_operand:MODEF 1 "register_operand" "x")
1605           (match_operand:MODEF 2 "register_operand" "x")))]
1606   "AVX_FLOAT_MODE_P (<MODE>mode)"
1607   "v<plogicprefix>p<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
1608   [(set_attr "type" "sselog")
1609    (set_attr "prefix" "vex")
1610    (set_attr "mode" "<ssevecmode>")])
1611
1612 (define_insn "*<code><mode>3"
1613   [(set (match_operand:MODEF 0 "register_operand" "=x")
1614         (plogic:MODEF
1615           (match_operand:MODEF 1 "register_operand" "0")
1616           (match_operand:MODEF 2 "register_operand" "x")))]
1617   "SSE_FLOAT_MODE_P (<MODE>mode)"
1618   "<plogicprefix>p<ssemodefsuffix>\t{%2, %0|%0, %2}"
1619   [(set_attr "type" "sselog")
1620    (set_attr "mode" "<ssevecmode>")])
1621
1622 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1623 ;;
1624 ;; SSE5 floating point multiply/accumulate instructions This includes the
1625 ;; scalar version of the instructions as well as the vector
1626 ;;
1627 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1628
1629 ;; In order to match (*a * *b) + *c, particularly when vectorizing, allow
1630 ;; combine to generate a multiply/add with two memory references.  We then
1631 ;; split this insn, into loading up the destination register with one of the
1632 ;; memory operations.  If we don't manage to split the insn, reload will
1633 ;; generate the appropriate moves.  The reason this is needed, is that combine
1634 ;; has already folded one of the memory references into both the multiply and
1635 ;; add insns, and it can't generate a new pseudo.  I.e.:
1636 ;;      (set (reg1) (mem (addr1)))
1637 ;;      (set (reg2) (mult (reg1) (mem (addr2))))
1638 ;;      (set (reg3) (plus (reg2) (mem (addr3))))
1639
1640 (define_insn "sse5_fmadd<mode>4"
1641   [(set (match_operand:SSEMODEF4 0 "register_operand" "=x,x,x,x")
1642         (plus:SSEMODEF4
1643          (mult:SSEMODEF4
1644           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "%0,0,x,xm")
1645           (match_operand:SSEMODEF4 2 "nonimmediate_operand" "x,xm,xm,x"))
1646          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "xm,x,0,0")))]
1647   "TARGET_SSE5 && TARGET_FUSED_MADD
1648    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)"
1649   "fmadd<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1650   [(set_attr "type" "ssemuladd")
1651    (set_attr "mode" "<MODE>")])
1652
1653 ;; Split fmadd with two memory operands into a load and the fmadd.
1654 (define_split
1655   [(set (match_operand:SSEMODEF4 0 "register_operand" "")
1656         (plus:SSEMODEF4
1657          (mult:SSEMODEF4
1658           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "")
1659           (match_operand:SSEMODEF4 2 "nonimmediate_operand" ""))
1660          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "")))]
1661   "TARGET_SSE5
1662    && !ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)
1663    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)
1664    && !reg_mentioned_p (operands[0], operands[1])
1665    && !reg_mentioned_p (operands[0], operands[2])
1666    && !reg_mentioned_p (operands[0], operands[3])"
1667   [(const_int 0)]
1668 {
1669   ix86_expand_sse5_multiple_memory (operands, 4, <MODE>mode);
1670   emit_insn (gen_sse5_fmadd<mode>4 (operands[0], operands[1],
1671                                     operands[2], operands[3]));
1672   DONE;
1673 })
1674
1675 ;; For the scalar operations, use operand1 for the upper words that aren't
1676 ;; modified, so restrict the forms that are generated.
1677 ;; Scalar version of fmadd
1678 (define_insn "sse5_vmfmadd<mode>4"
1679   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
1680         (vec_merge:SSEMODEF2P
1681          (plus:SSEMODEF2P
1682           (mult:SSEMODEF2P
1683            (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0")
1684            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
1685           (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
1686          (match_dup 1)
1687          (const_int 1)))]
1688   "TARGET_SSE5 && TARGET_FUSED_MADD
1689    && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
1690   "fmadd<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1691   [(set_attr "type" "ssemuladd")
1692    (set_attr "mode" "<MODE>")])
1693
1694 ;; Floating multiply and subtract
1695 ;; Allow two memory operands the same as fmadd
1696 (define_insn "sse5_fmsub<mode>4"
1697   [(set (match_operand:SSEMODEF4 0 "register_operand" "=x,x,x,x")
1698         (minus:SSEMODEF4
1699          (mult:SSEMODEF4
1700           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "%0,0,x,xm")
1701           (match_operand:SSEMODEF4 2 "nonimmediate_operand" "x,xm,xm,x"))
1702          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "xm,x,0,0")))]
1703   "TARGET_SSE5 && TARGET_FUSED_MADD
1704    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)"
1705   "fmsub<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1706   [(set_attr "type" "ssemuladd")
1707    (set_attr "mode" "<MODE>")])
1708
1709 ;; Split fmsub with two memory operands into a load and the fmsub.
1710 (define_split
1711   [(set (match_operand:SSEMODEF4 0 "register_operand" "")
1712         (minus:SSEMODEF4
1713          (mult:SSEMODEF4
1714           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "")
1715           (match_operand:SSEMODEF4 2 "nonimmediate_operand" ""))
1716          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "")))]
1717   "TARGET_SSE5
1718    && !ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)
1719    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)
1720    && !reg_mentioned_p (operands[0], operands[1])
1721    && !reg_mentioned_p (operands[0], operands[2])
1722    && !reg_mentioned_p (operands[0], operands[3])"
1723   [(const_int 0)]
1724 {
1725   ix86_expand_sse5_multiple_memory (operands, 4, <MODE>mode);
1726   emit_insn (gen_sse5_fmsub<mode>4 (operands[0], operands[1],
1727                                     operands[2], operands[3]));
1728   DONE;
1729 })
1730
1731 ;; For the scalar operations, use operand1 for the upper words that aren't
1732 ;; modified, so restrict the forms that are generated.
1733 ;; Scalar version of fmsub
1734 (define_insn "sse5_vmfmsub<mode>4"
1735   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
1736         (vec_merge:SSEMODEF2P
1737          (minus:SSEMODEF2P
1738           (mult:SSEMODEF2P
1739            (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0")
1740            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
1741           (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
1742          (match_dup 1)
1743          (const_int 1)))]
1744   "TARGET_SSE5 && TARGET_FUSED_MADD
1745    && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
1746   "fmsub<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1747   [(set_attr "type" "ssemuladd")
1748    (set_attr "mode" "<MODE>")])
1749
1750 ;; Floating point negative multiply and add
1751 ;; Rewrite (- (a * b) + c) into the canonical form: c - (a * b)
1752 ;; Note operands are out of order to simplify call to ix86_sse5_valid_p
1753 ;; Allow two memory operands to help in optimizing.
1754 (define_insn "sse5_fnmadd<mode>4"
1755   [(set (match_operand:SSEMODEF4 0 "register_operand" "=x,x,x,x")
1756         (minus:SSEMODEF4
1757          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "xm,x,0,0")
1758          (mult:SSEMODEF4
1759           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "%0,0,x,xm")
1760           (match_operand:SSEMODEF4 2 "nonimmediate_operand" "x,xm,xm,x"))))]
1761   "TARGET_SSE5 && TARGET_FUSED_MADD
1762    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)"
1763   "fnmadd<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1764   [(set_attr "type" "ssemuladd")
1765    (set_attr "mode" "<MODE>")])
1766
1767 ;; Split fnmadd with two memory operands into a load and the fnmadd.
1768 (define_split
1769   [(set (match_operand:SSEMODEF4 0 "register_operand" "")
1770         (minus:SSEMODEF4
1771          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "")
1772          (mult:SSEMODEF4
1773           (match_operand:SSEMODEF4 1 "nonimmediate_operand" "")
1774           (match_operand:SSEMODEF4 2 "nonimmediate_operand" ""))))]
1775   "TARGET_SSE5
1776    && !ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)
1777    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, true)
1778    && !reg_mentioned_p (operands[0], operands[1])
1779    && !reg_mentioned_p (operands[0], operands[2])
1780    && !reg_mentioned_p (operands[0], operands[3])"
1781   [(const_int 0)]
1782 {
1783   ix86_expand_sse5_multiple_memory (operands, 4, <MODE>mode);
1784   emit_insn (gen_sse5_fnmadd<mode>4 (operands[0], operands[1],
1785                                      operands[2], operands[3]));
1786   DONE;
1787 })
1788
1789 ;; For the scalar operations, use operand1 for the upper words that aren't
1790 ;; modified, so restrict the forms that are generated.
1791 ;; Scalar version of fnmadd
1792 (define_insn "sse5_vmfnmadd<mode>4"
1793   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
1794         (vec_merge:SSEMODEF2P
1795          (minus:SSEMODEF2P
1796           (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x")
1797           (mult:SSEMODEF2P
1798            (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0")
1799            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm")))
1800          (match_dup 1)
1801          (const_int 1)))]
1802   "TARGET_SSE5 && TARGET_FUSED_MADD
1803    && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
1804   "fnmadd<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1805   [(set_attr "type" "ssemuladd")
1806    (set_attr "mode" "<MODE>")])
1807
1808 ;; Floating point negative multiply and subtract
1809 ;; Rewrite (- (a * b) - c) into the canonical form: ((-a) * b) - c
1810 ;; Allow 2 memory operands to help with optimization
1811 (define_insn "sse5_fnmsub<mode>4"
1812   [(set (match_operand:SSEMODEF4 0 "register_operand" "=x,x")
1813         (minus:SSEMODEF4
1814          (mult:SSEMODEF4
1815           (neg:SSEMODEF4
1816            (match_operand:SSEMODEF4 1 "nonimmediate_operand" "0,0"))
1817           (match_operand:SSEMODEF4 2 "nonimmediate_operand" "x,xm"))
1818          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "xm,x")))]
1819   "TARGET_SSE5 && TARGET_FUSED_MADD
1820    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, false)"
1821   "fnmsub<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1822   [(set_attr "type" "ssemuladd")
1823    (set_attr "mode" "<MODE>")])
1824
1825 ;; Split fnmsub with two memory operands into a load and the fmsub.
1826 (define_split
1827   [(set (match_operand:SSEMODEF4 0 "register_operand" "")
1828         (minus:SSEMODEF4
1829          (mult:SSEMODEF4
1830           (neg:SSEMODEF4
1831            (match_operand:SSEMODEF4 1 "nonimmediate_operand" ""))
1832           (match_operand:SSEMODEF4 2 "nonimmediate_operand" ""))
1833          (match_operand:SSEMODEF4 3 "nonimmediate_operand" "")))]
1834   "TARGET_SSE5
1835    && !ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)
1836    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, false)
1837    && !reg_mentioned_p (operands[0], operands[1])
1838    && !reg_mentioned_p (operands[0], operands[2])
1839    && !reg_mentioned_p (operands[0], operands[3])"
1840   [(const_int 0)]
1841 {
1842   ix86_expand_sse5_multiple_memory (operands, 4, <MODE>mode);
1843   emit_insn (gen_sse5_fnmsub<mode>4 (operands[0], operands[1],
1844                                      operands[2], operands[3]));
1845   DONE;
1846 })
1847
1848 ;; For the scalar operations, use operand1 for the upper words that aren't
1849 ;; modified, so restrict the forms that are generated.
1850 ;; Scalar version of fnmsub
1851 (define_insn "sse5_vmfnmsub<mode>4"
1852   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
1853         (vec_merge:SSEMODEF2P
1854          (minus:SSEMODEF2P
1855           (mult:SSEMODEF2P
1856            (neg:SSEMODEF2P
1857             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0"))
1858            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
1859           (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
1860          (match_dup 1)
1861          (const_int 1)))]
1862   "TARGET_SSE5 && TARGET_FUSED_MADD
1863    && ix86_sse5_valid_op_p (operands, insn, 4, true, 2, false)"
1864   "fnmsub<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1865   [(set_attr "type" "ssemuladd")
1866    (set_attr "mode" "<MODE>")])
1867
1868 ;; The same instructions using an UNSPEC to allow the intrinsic to be used
1869 ;; even if the user used -mno-fused-madd
1870 ;; Parallel instructions.  During instruction generation, just default
1871 ;; to registers, and let combine later build the appropriate instruction.
1872 (define_expand "sse5i_fmadd<mode>4"
1873   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1874         (unspec:SSEMODEF2P
1875          [(plus:SSEMODEF2P
1876            (mult:SSEMODEF2P
1877             (match_operand:SSEMODEF2P 1 "register_operand" "")
1878             (match_operand:SSEMODEF2P 2 "register_operand" ""))
1879            (match_operand:SSEMODEF2P 3 "register_operand" ""))]
1880          UNSPEC_SSE5_INTRINSIC))]
1881   "TARGET_SSE5"
1882 {
1883   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
1884   if (TARGET_FUSED_MADD)
1885     {
1886       emit_insn (gen_sse5_fmadd<mode>4 (operands[0], operands[1],
1887                                         operands[2], operands[3]));
1888       DONE;
1889     }
1890 })
1891
1892 (define_insn "*sse5i_fmadd<mode>4"
1893   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x,x,x")
1894         (unspec:SSEMODEF2P
1895          [(plus:SSEMODEF2P
1896            (mult:SSEMODEF2P
1897             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0,0,x,xm")
1898             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm,xm,x"))
1899            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x,0,0"))]
1900          UNSPEC_SSE5_INTRINSIC))]
1901   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
1902   "fmadd<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1903   [(set_attr "type" "ssemuladd")
1904    (set_attr "mode" "<MODE>")])
1905
1906 (define_expand "sse5i_fmsub<mode>4"
1907   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1908         (unspec:SSEMODEF2P
1909          [(minus:SSEMODEF2P
1910            (mult:SSEMODEF2P
1911             (match_operand:SSEMODEF2P 1 "register_operand" "")
1912             (match_operand:SSEMODEF2P 2 "register_operand" ""))
1913            (match_operand:SSEMODEF2P 3 "register_operand" ""))]
1914          UNSPEC_SSE5_INTRINSIC))]
1915   "TARGET_SSE5"
1916 {
1917   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
1918   if (TARGET_FUSED_MADD)
1919     {
1920       emit_insn (gen_sse5_fmsub<mode>4 (operands[0], operands[1],
1921                                         operands[2], operands[3]));
1922       DONE;
1923     }
1924 })
1925
1926 (define_insn "*sse5i_fmsub<mode>4"
1927   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x,x,x")
1928         (unspec:SSEMODEF2P
1929          [(minus:SSEMODEF2P
1930            (mult:SSEMODEF2P
1931             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0,0,x,xm")
1932             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm,xm,x"))
1933            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x,0,0"))]
1934          UNSPEC_SSE5_INTRINSIC))]
1935   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
1936   "fmsub<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1937   [(set_attr "type" "ssemuladd")
1938    (set_attr "mode" "<MODE>")])
1939
1940 ;; Rewrite (- (a * b) + c) into the canonical form: c - (a * b)
1941 ;; Note operands are out of order to simplify call to ix86_sse5_valid_p
1942 (define_expand "sse5i_fnmadd<mode>4"
1943   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1944         (unspec:SSEMODEF2P
1945          [(minus:SSEMODEF2P
1946            (match_operand:SSEMODEF2P 3 "register_operand" "")
1947            (mult:SSEMODEF2P
1948             (match_operand:SSEMODEF2P 1 "register_operand" "")
1949             (match_operand:SSEMODEF2P 2 "register_operand" "")))]
1950          UNSPEC_SSE5_INTRINSIC))]
1951   "TARGET_SSE5"
1952 {
1953   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
1954   if (TARGET_FUSED_MADD)
1955     {
1956       emit_insn (gen_sse5_fnmadd<mode>4 (operands[0], operands[1],
1957                                          operands[2], operands[3]));
1958       DONE;
1959     }
1960 })
1961
1962 (define_insn "*sse5i_fnmadd<mode>4"
1963   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x,x,x")
1964         (unspec:SSEMODEF2P
1965          [(minus:SSEMODEF2P
1966            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x,0,0")
1967            (mult:SSEMODEF2P
1968             (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0,0,x,xm")
1969             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm,xm,x")))]
1970          UNSPEC_SSE5_INTRINSIC))]
1971   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
1972   "fnmadd<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1973   [(set_attr "type" "ssemuladd")
1974    (set_attr "mode" "<MODE>")])
1975
1976 ;; Rewrite (- (a * b) - c) into the canonical form: ((-a) * b) - c
1977 (define_expand "sse5i_fnmsub<mode>4"
1978   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
1979         (unspec:SSEMODEF2P
1980          [(minus:SSEMODEF2P
1981            (mult:SSEMODEF2P
1982             (neg:SSEMODEF2P
1983              (match_operand:SSEMODEF2P 1 "register_operand" ""))
1984             (match_operand:SSEMODEF2P 2 "register_operand" ""))
1985            (match_operand:SSEMODEF2P 3 "register_operand" ""))]
1986          UNSPEC_SSE5_INTRINSIC))]
1987   "TARGET_SSE5"
1988 {
1989   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
1990   if (TARGET_FUSED_MADD)
1991     {
1992       emit_insn (gen_sse5_fnmsub<mode>4 (operands[0], operands[1],
1993                                          operands[2], operands[3]));
1994       DONE;
1995     }
1996 })
1997
1998 (define_insn "*sse5i_fnmsub<mode>4"
1999   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x,x,x")
2000         (unspec:SSEMODEF2P
2001          [(minus:SSEMODEF2P
2002            (mult:SSEMODEF2P
2003             (neg:SSEMODEF2P
2004              (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0,x,xm"))
2005             (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm,xm,x"))
2006            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x,0,0"))]
2007          UNSPEC_SSE5_INTRINSIC))]
2008   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
2009   "fnmsub<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
2010   [(set_attr "type" "ssemuladd")
2011    (set_attr "mode" "<MODE>")])
2012
2013 ;; Scalar instructions
2014 (define_expand "sse5i_vmfmadd<mode>4"
2015   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
2016         (unspec:SSEMODEF2P
2017          [(vec_merge:SSEMODEF2P
2018            (plus:SSEMODEF2P
2019             (mult:SSEMODEF2P
2020              (match_operand:SSEMODEF2P 1 "register_operand" "")
2021              (match_operand:SSEMODEF2P 2 "register_operand" ""))
2022             (match_operand:SSEMODEF2P 3 "register_operand" ""))
2023            (match_dup 1)
2024            (const_int 0))]
2025          UNSPEC_SSE5_INTRINSIC))]
2026   "TARGET_SSE5"
2027 {
2028   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
2029   if (TARGET_FUSED_MADD)
2030     {
2031       emit_insn (gen_sse5_vmfmadd<mode>4 (operands[0], operands[1],
2032                                           operands[2], operands[3]));
2033       DONE;
2034     }
2035 })
2036
2037 ;; For the scalar operations, use operand1 for the upper words that aren't
2038 ;; modified, so restrict the forms that are accepted.
2039 (define_insn "*sse5i_vmfmadd<mode>4"
2040   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
2041         (unspec:SSEMODEF2P
2042          [(vec_merge:SSEMODEF2P
2043            (plus:SSEMODEF2P
2044             (mult:SSEMODEF2P
2045              (match_operand:SSEMODEF2P 1 "register_operand" "0,0")
2046              (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
2047             (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
2048            (match_dup 0)
2049            (const_int 0))]
2050          UNSPEC_SSE5_INTRINSIC))]
2051   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
2052   "fmadd<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
2053   [(set_attr "type" "ssemuladd")
2054    (set_attr "mode" "<ssescalarmode>")])
2055
2056 (define_expand "sse5i_vmfmsub<mode>4"
2057   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
2058         (unspec:SSEMODEF2P
2059          [(vec_merge:SSEMODEF2P
2060            (minus:SSEMODEF2P
2061             (mult:SSEMODEF2P
2062              (match_operand:SSEMODEF2P 1 "register_operand" "")
2063              (match_operand:SSEMODEF2P 2 "register_operand" ""))
2064             (match_operand:SSEMODEF2P 3 "register_operand" ""))
2065            (match_dup 0)
2066            (const_int 1))]
2067          UNSPEC_SSE5_INTRINSIC))]
2068   "TARGET_SSE5"
2069 {
2070   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
2071   if (TARGET_FUSED_MADD)
2072     {
2073       emit_insn (gen_sse5_vmfmsub<mode>4 (operands[0], operands[1],
2074                                           operands[2], operands[3]));
2075       DONE;
2076     }
2077 })
2078
2079 (define_insn "*sse5i_vmfmsub<mode>4"
2080   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
2081         (unspec:SSEMODEF2P
2082          [(vec_merge:SSEMODEF2P
2083            (minus:SSEMODEF2P
2084             (mult:SSEMODEF2P
2085              (match_operand:SSEMODEF2P 1 "register_operand" "0,0")
2086              (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
2087             (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
2088            (match_dup 1)
2089            (const_int 1))]
2090          UNSPEC_SSE5_INTRINSIC))]
2091   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
2092   "fmsub<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
2093   [(set_attr "type" "ssemuladd")
2094    (set_attr "mode" "<ssescalarmode>")])
2095
2096 ;; Note operands are out of order to simplify call to ix86_sse5_valid_p
2097 (define_expand "sse5i_vmfnmadd<mode>4"
2098   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
2099         (unspec:SSEMODEF2P
2100          [(vec_merge:SSEMODEF2P
2101            (minus:SSEMODEF2P
2102             (match_operand:SSEMODEF2P 3 "register_operand" "")
2103             (mult:SSEMODEF2P
2104              (match_operand:SSEMODEF2P 1 "register_operand" "")
2105              (match_operand:SSEMODEF2P 2 "register_operand" "")))
2106            (match_dup 1)
2107            (const_int 1))]
2108          UNSPEC_SSE5_INTRINSIC))]
2109   "TARGET_SSE5"
2110 {
2111   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
2112   if (TARGET_FUSED_MADD)
2113     {
2114       emit_insn (gen_sse5_vmfnmadd<mode>4 (operands[0], operands[1],
2115                                            operands[2], operands[3]));
2116       DONE;
2117     }
2118 })
2119
2120 (define_insn "*sse5i_vmfnmadd<mode>4"
2121   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
2122         (unspec:SSEMODEF2P
2123          [(vec_merge:SSEMODEF2P
2124            (minus:SSEMODEF2P
2125             (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x")
2126             (mult:SSEMODEF2P
2127              (match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0,0")
2128              (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm")))
2129            (match_dup 1)
2130            (const_int 1))]
2131          UNSPEC_SSE5_INTRINSIC))]
2132   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, true)"
2133   "fnmadd<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
2134   [(set_attr "type" "ssemuladd")
2135    (set_attr "mode" "<ssescalarmode>")])
2136
2137 (define_expand "sse5i_vmfnmsub<mode>4"
2138   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
2139         (unspec:SSEMODEF2P
2140          [(vec_merge:SSEMODEF2P
2141            (minus:SSEMODEF2P
2142             (mult:SSEMODEF2P
2143              (neg:SSEMODEF2P
2144               (match_operand:SSEMODEF2P 1 "register_operand" ""))
2145              (match_operand:SSEMODEF2P 2 "register_operand" ""))
2146             (match_operand:SSEMODEF2P 3 "register_operand" ""))
2147            (match_dup 1)
2148            (const_int 1))]
2149          UNSPEC_SSE5_INTRINSIC))]
2150   "TARGET_SSE5"
2151 {
2152   /* If we have -mfused-madd, emit the normal insn rather than the UNSPEC */
2153   if (TARGET_FUSED_MADD)
2154     {
2155       emit_insn (gen_sse5_vmfnmsub<mode>4 (operands[0], operands[1],
2156                                            operands[2], operands[3]));
2157       DONE;
2158     }
2159 })
2160
2161 (define_insn "*sse5i_vmfnmsub<mode>4"
2162   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x")
2163         (unspec:SSEMODEF2P
2164          [(vec_merge:SSEMODEF2P
2165            (minus:SSEMODEF2P
2166             (mult:SSEMODEF2P
2167              (neg:SSEMODEF2P
2168               (match_operand:SSEMODEF2P 1 "register_operand" "0,0"))
2169              (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm"))
2170             (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm,x"))
2171            (match_dup 1)
2172            (const_int 1))]
2173          UNSPEC_SSE5_INTRINSIC))]
2174   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
2175   "fnmsub<ssemodesuffixf2s>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
2176   [(set_attr "type" "ssemuladd")
2177    (set_attr "mode" "<ssescalarmode>")])
2178
2179 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2180 ;;
2181 ;; Parallel single-precision floating point conversion operations
2182 ;;
2183 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2184
2185 (define_insn "sse_cvtpi2ps"
2186   [(set (match_operand:V4SF 0 "register_operand" "=x")
2187         (vec_merge:V4SF
2188           (vec_duplicate:V4SF
2189             (float:V2SF (match_operand:V2SI 2 "nonimmediate_operand" "ym")))
2190           (match_operand:V4SF 1 "register_operand" "0")
2191           (const_int 3)))]
2192   "TARGET_SSE"
2193   "cvtpi2ps\t{%2, %0|%0, %2}"
2194   [(set_attr "type" "ssecvt")
2195    (set_attr "mode" "V4SF")])
2196
2197 (define_insn "sse_cvtps2pi"
2198   [(set (match_operand:V2SI 0 "register_operand" "=y")
2199         (vec_select:V2SI
2200           (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
2201                        UNSPEC_FIX_NOTRUNC)
2202           (parallel [(const_int 0) (const_int 1)])))]
2203   "TARGET_SSE"
2204   "cvtps2pi\t{%1, %0|%0, %1}"
2205   [(set_attr "type" "ssecvt")
2206    (set_attr "unit" "mmx")
2207    (set_attr "mode" "DI")])
2208
2209 (define_insn "sse_cvttps2pi"
2210   [(set (match_operand:V2SI 0 "register_operand" "=y")
2211         (vec_select:V2SI
2212           (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm"))
2213           (parallel [(const_int 0) (const_int 1)])))]
2214   "TARGET_SSE"
2215   "cvttps2pi\t{%1, %0|%0, %1}"
2216   [(set_attr "type" "ssecvt")
2217    (set_attr "unit" "mmx")
2218    (set_attr "mode" "SF")])
2219
2220 (define_insn "*avx_cvtsi2ss"
2221   [(set (match_operand:V4SF 0 "register_operand" "=x")
2222         (vec_merge:V4SF
2223           (vec_duplicate:V4SF
2224             (float:SF (match_operand:SI 2 "nonimmediate_operand" "rm")))
2225           (match_operand:V4SF 1 "register_operand" "x")
2226           (const_int 1)))]
2227   "TARGET_AVX"
2228   "vcvtsi2ss\t{%2, %1, %0|%0, %1, %2}"
2229   [(set_attr "type" "sseicvt")
2230    (set_attr "prefix" "vex")
2231    (set_attr "mode" "SF")])
2232
2233 (define_insn "sse_cvtsi2ss"
2234   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
2235         (vec_merge:V4SF
2236           (vec_duplicate:V4SF
2237             (float:SF (match_operand:SI 2 "nonimmediate_operand" "r,m")))
2238           (match_operand:V4SF 1 "register_operand" "0,0")
2239           (const_int 1)))]
2240   "TARGET_SSE"
2241   "cvtsi2ss\t{%2, %0|%0, %2}"
2242   [(set_attr "type" "sseicvt")
2243    (set_attr "athlon_decode" "vector,double")
2244    (set_attr "amdfam10_decode" "vector,double")
2245    (set_attr "mode" "SF")])
2246
2247 (define_insn "*avx_cvtsi2ssq"
2248   [(set (match_operand:V4SF 0 "register_operand" "=x")
2249         (vec_merge:V4SF
2250           (vec_duplicate:V4SF
2251             (float:SF (match_operand:DI 2 "nonimmediate_operand" "rm")))
2252           (match_operand:V4SF 1 "register_operand" "x")
2253           (const_int 1)))]
2254   "TARGET_AVX && TARGET_64BIT"
2255   "vcvtsi2ssq\t{%2, %1, %0|%0, %1, %2}"
2256   [(set_attr "type" "sseicvt")
2257    (set_attr "prefix" "vex")
2258    (set_attr "mode" "SF")])
2259
2260 (define_insn "sse_cvtsi2ssq"
2261   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
2262         (vec_merge:V4SF
2263           (vec_duplicate:V4SF
2264             (float:SF (match_operand:DI 2 "nonimmediate_operand" "r,rm")))
2265           (match_operand:V4SF 1 "register_operand" "0,0")
2266           (const_int 1)))]
2267   "TARGET_SSE && TARGET_64BIT"
2268   "cvtsi2ssq\t{%2, %0|%0, %2}"
2269   [(set_attr "type" "sseicvt")
2270    (set_attr "athlon_decode" "vector,double")
2271    (set_attr "amdfam10_decode" "vector,double")
2272    (set_attr "mode" "SF")])
2273
2274 (define_insn "sse_cvtss2si"
2275   [(set (match_operand:SI 0 "register_operand" "=r,r")
2276         (unspec:SI
2277           [(vec_select:SF
2278              (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2279              (parallel [(const_int 0)]))]
2280           UNSPEC_FIX_NOTRUNC))]
2281   "TARGET_SSE"
2282   "%vcvtss2si\t{%1, %0|%0, %1}"
2283   [(set_attr "type" "sseicvt")
2284    (set_attr "athlon_decode" "double,vector")
2285    (set_attr "prefix_rep" "1")
2286    (set_attr "prefix" "maybe_vex")
2287    (set_attr "mode" "SI")])
2288
2289 (define_insn "sse_cvtss2si_2"
2290   [(set (match_operand:SI 0 "register_operand" "=r,r")
2291         (unspec:SI [(match_operand:SF 1 "nonimmediate_operand" "x,m")]
2292                    UNSPEC_FIX_NOTRUNC))]
2293   "TARGET_SSE"
2294   "%vcvtss2si\t{%1, %0|%0, %1}"
2295   [(set_attr "type" "sseicvt")
2296    (set_attr "athlon_decode" "double,vector")
2297    (set_attr "amdfam10_decode" "double,double")
2298    (set_attr "prefix_rep" "1")
2299    (set_attr "prefix" "maybe_vex")
2300    (set_attr "mode" "SI")])
2301
2302 (define_insn "sse_cvtss2siq"
2303   [(set (match_operand:DI 0 "register_operand" "=r,r")
2304         (unspec:DI
2305           [(vec_select:SF
2306              (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2307              (parallel [(const_int 0)]))]
2308           UNSPEC_FIX_NOTRUNC))]
2309   "TARGET_SSE && TARGET_64BIT"
2310   "%vcvtss2si{q}\t{%1, %0|%0, %1}"
2311   [(set_attr "type" "sseicvt")
2312    (set_attr "athlon_decode" "double,vector")
2313    (set_attr "prefix_rep" "1")
2314    (set_attr "prefix" "maybe_vex")
2315    (set_attr "mode" "DI")])
2316
2317 (define_insn "sse_cvtss2siq_2"
2318   [(set (match_operand:DI 0 "register_operand" "=r,r")
2319         (unspec:DI [(match_operand:SF 1 "nonimmediate_operand" "x,m")]
2320                    UNSPEC_FIX_NOTRUNC))]
2321   "TARGET_SSE && TARGET_64BIT"
2322   "%vcvtss2si{q}\t{%1, %0|%0, %1}"
2323   [(set_attr "type" "sseicvt")
2324    (set_attr "athlon_decode" "double,vector")
2325    (set_attr "amdfam10_decode" "double,double")
2326    (set_attr "prefix_rep" "1")
2327    (set_attr "prefix" "maybe_vex")
2328    (set_attr "mode" "DI")])
2329
2330 (define_insn "sse_cvttss2si"
2331   [(set (match_operand:SI 0 "register_operand" "=r,r")
2332         (fix:SI
2333           (vec_select:SF
2334             (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2335             (parallel [(const_int 0)]))))]
2336   "TARGET_SSE"
2337   "%vcvttss2si\t{%1, %0|%0, %1}"
2338   [(set_attr "type" "sseicvt")
2339    (set_attr "athlon_decode" "double,vector")
2340    (set_attr "amdfam10_decode" "double,double")
2341    (set_attr "prefix_rep" "1")
2342    (set_attr "prefix" "maybe_vex")
2343    (set_attr "mode" "SI")])
2344
2345 (define_insn "sse_cvttss2siq"
2346   [(set (match_operand:DI 0 "register_operand" "=r,r")
2347         (fix:DI
2348           (vec_select:SF
2349             (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2350             (parallel [(const_int 0)]))))]
2351   "TARGET_SSE && TARGET_64BIT"
2352   "%vcvttss2si{q}\t{%1, %0|%0, %1}"
2353   [(set_attr "type" "sseicvt")
2354    (set_attr "athlon_decode" "double,vector")
2355    (set_attr "amdfam10_decode" "double,double")
2356    (set_attr "prefix_rep" "1")
2357    (set_attr "prefix" "maybe_vex")
2358    (set_attr "mode" "DI")])
2359
2360 (define_insn "avx_cvtdq2ps<avxmodesuffix>"
2361   [(set (match_operand:AVXMODEDCVTDQ2PS 0 "register_operand" "=x")
2362         (float:AVXMODEDCVTDQ2PS
2363           (match_operand:<avxcvtvecmode> 1 "nonimmediate_operand" "xm")))]
2364   "TARGET_AVX"
2365   "vcvtdq2ps\t{%1, %0|%0, %1}"
2366   [(set_attr "type" "ssecvt")
2367    (set_attr "prefix" "vex")
2368    (set_attr "mode" "<avxvecmode>")])
2369
2370 (define_insn "sse2_cvtdq2ps"
2371   [(set (match_operand:V4SF 0 "register_operand" "=x")
2372         (float:V4SF (match_operand:V4SI 1 "nonimmediate_operand" "xm")))]
2373   "TARGET_SSE2"
2374   "cvtdq2ps\t{%1, %0|%0, %1}"
2375   [(set_attr "type" "ssecvt")
2376    (set_attr "mode" "V4SF")])
2377
2378 (define_insn "avx_cvtps2dq<avxmodesuffix>"
2379   [(set (match_operand:AVXMODEDCVTPS2DQ 0 "register_operand" "=x")
2380         (unspec:AVXMODEDCVTPS2DQ
2381           [(match_operand:<avxcvtvecmode> 1 "nonimmediate_operand" "xm")]
2382           UNSPEC_FIX_NOTRUNC))]
2383   "TARGET_AVX"
2384   "vcvtps2dq\t{%1, %0|%0, %1}"
2385   [(set_attr "type" "ssecvt")
2386    (set_attr "prefix" "vex")
2387    (set_attr "mode" "<avxvecmode>")])
2388
2389 (define_insn "sse2_cvtps2dq"
2390   [(set (match_operand:V4SI 0 "register_operand" "=x")
2391         (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
2392                      UNSPEC_FIX_NOTRUNC))]
2393   "TARGET_SSE2"
2394   "cvtps2dq\t{%1, %0|%0, %1}"
2395   [(set_attr "type" "ssecvt")
2396    (set_attr "prefix_data16" "1")
2397    (set_attr "mode" "TI")])
2398
2399 (define_insn "avx_cvttps2dq<avxmodesuffix>"
2400   [(set (match_operand:AVXMODEDCVTPS2DQ 0 "register_operand" "=x")
2401         (fix:AVXMODEDCVTPS2DQ
2402           (match_operand:<avxcvtvecmode> 1 "nonimmediate_operand" "xm")))]
2403   "TARGET_AVX"
2404   "vcvttps2dq\t{%1, %0|%0, %1}"
2405   [(set_attr "type" "ssecvt")
2406    (set_attr "prefix" "vex")
2407    (set_attr "mode" "<avxvecmode>")])
2408
2409 (define_insn "sse2_cvttps2dq"
2410   [(set (match_operand:V4SI 0 "register_operand" "=x")
2411         (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
2412   "TARGET_SSE2"
2413   "cvttps2dq\t{%1, %0|%0, %1}"
2414   [(set_attr "type" "ssecvt")
2415    (set_attr "prefix_rep" "1")
2416    (set_attr "mode" "TI")])
2417
2418 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2419 ;;
2420 ;; Parallel double-precision floating point conversion operations
2421 ;;
2422 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2423
2424 (define_insn "sse2_cvtpi2pd"
2425   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
2426         (float:V2DF (match_operand:V2SI 1 "nonimmediate_operand" "y,m")))]
2427   "TARGET_SSE2"
2428   "cvtpi2pd\t{%1, %0|%0, %1}"
2429   [(set_attr "type" "ssecvt")
2430    (set_attr "unit" "mmx,*")
2431    (set_attr "mode" "V2DF")])
2432
2433 (define_insn "sse2_cvtpd2pi"
2434   [(set (match_operand:V2SI 0 "register_operand" "=y")
2435         (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
2436                      UNSPEC_FIX_NOTRUNC))]
2437   "TARGET_SSE2"
2438   "cvtpd2pi\t{%1, %0|%0, %1}"
2439   [(set_attr "type" "ssecvt")
2440    (set_attr "unit" "mmx")
2441    (set_attr "prefix_data16" "1")
2442    (set_attr "mode" "DI")])
2443
2444 (define_insn "sse2_cvttpd2pi"
2445   [(set (match_operand:V2SI 0 "register_operand" "=y")
2446         (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm")))]
2447   "TARGET_SSE2"
2448   "cvttpd2pi\t{%1, %0|%0, %1}"
2449   [(set_attr "type" "ssecvt")
2450    (set_attr "unit" "mmx")
2451    (set_attr "prefix_data16" "1")
2452    (set_attr "mode" "TI")])
2453
2454 (define_insn "*avx_cvtsi2sd"
2455   [(set (match_operand:V2DF 0 "register_operand" "=x")
2456         (vec_merge:V2DF
2457           (vec_duplicate:V2DF
2458             (float:DF (match_operand:SI 2 "nonimmediate_operand" "rm")))
2459           (match_operand:V2DF 1 "register_operand" "x")
2460           (const_int 1)))]
2461   "TARGET_AVX"
2462   "vcvtsi2sd\t{%2, %1, %0|%0, %1, %2}"
2463   [(set_attr "type" "sseicvt")
2464    (set_attr "prefix" "vex")
2465    (set_attr "mode" "DF")])
2466
2467 (define_insn "sse2_cvtsi2sd"
2468   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
2469         (vec_merge:V2DF
2470           (vec_duplicate:V2DF
2471             (float:DF (match_operand:SI 2 "nonimmediate_operand" "r,m")))
2472           (match_operand:V2DF 1 "register_operand" "0,0")
2473           (const_int 1)))]
2474   "TARGET_SSE2"
2475   "cvtsi2sd\t{%2, %0|%0, %2}"
2476   [(set_attr "type" "sseicvt")
2477    (set_attr "mode" "DF")
2478    (set_attr "athlon_decode" "double,direct")
2479    (set_attr "amdfam10_decode" "vector,double")])
2480
2481 (define_insn "*avx_cvtsi2sdq"
2482   [(set (match_operand:V2DF 0 "register_operand" "=x")
2483         (vec_merge:V2DF
2484           (vec_duplicate:V2DF
2485             (float:DF (match_operand:DI 2 "nonimmediate_operand" "rm")))
2486           (match_operand:V2DF 1 "register_operand" "x")
2487           (const_int 1)))]
2488   "TARGET_AVX && TARGET_64BIT"
2489   "vcvtsi2sdq\t{%2, %1, %0|%0, %1, %2}"
2490   [(set_attr "type" "sseicvt")
2491    (set_attr "prefix" "vex")
2492    (set_attr "mode" "DF")])
2493
2494 (define_insn "sse2_cvtsi2sdq"
2495   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
2496         (vec_merge:V2DF
2497           (vec_duplicate:V2DF
2498             (float:DF (match_operand:DI 2 "nonimmediate_operand" "r,m")))
2499           (match_operand:V2DF 1 "register_operand" "0,0")
2500           (const_int 1)))]
2501   "TARGET_SSE2 && TARGET_64BIT"
2502   "cvtsi2sdq\t{%2, %0|%0, %2}"
2503   [(set_attr "type" "sseicvt")
2504    (set_attr "mode" "DF")
2505    (set_attr "athlon_decode" "double,direct")
2506    (set_attr "amdfam10_decode" "vector,double")])
2507
2508 (define_insn "sse2_cvtsd2si"
2509   [(set (match_operand:SI 0 "register_operand" "=r,r")
2510         (unspec:SI
2511           [(vec_select:DF
2512              (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2513              (parallel [(const_int 0)]))]
2514           UNSPEC_FIX_NOTRUNC))]
2515   "TARGET_SSE2"
2516   "%vcvtsd2si\t{%1, %0|%0, %1}"
2517   [(set_attr "type" "sseicvt")
2518    (set_attr "athlon_decode" "double,vector")
2519    (set_attr "prefix_rep" "1")
2520    (set_attr "prefix" "maybe_vex")
2521    (set_attr "mode" "SI")])
2522
2523 (define_insn "sse2_cvtsd2si_2"
2524   [(set (match_operand:SI 0 "register_operand" "=r,r")
2525         (unspec:SI [(match_operand:DF 1 "nonimmediate_operand" "x,m")]
2526                    UNSPEC_FIX_NOTRUNC))]
2527   "TARGET_SSE2"
2528   "%vcvtsd2si\t{%1, %0|%0, %1}"
2529   [(set_attr "type" "sseicvt")
2530    (set_attr "athlon_decode" "double,vector")
2531    (set_attr "amdfam10_decode" "double,double")
2532    (set_attr "prefix_rep" "1")
2533    (set_attr "prefix" "maybe_vex")
2534    (set_attr "mode" "SI")])
2535
2536 (define_insn "sse2_cvtsd2siq"
2537   [(set (match_operand:DI 0 "register_operand" "=r,r")
2538         (unspec:DI
2539           [(vec_select:DF
2540              (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2541              (parallel [(const_int 0)]))]
2542           UNSPEC_FIX_NOTRUNC))]
2543   "TARGET_SSE2 && TARGET_64BIT"
2544   "%vcvtsd2siq\t{%1, %0|%0, %1}"
2545   [(set_attr "type" "sseicvt")
2546    (set_attr "athlon_decode" "double,vector")
2547    (set_attr "prefix_rep" "1")
2548    (set_attr "prefix" "maybe_vex")
2549    (set_attr "mode" "DI")])
2550
2551 (define_insn "sse2_cvtsd2siq_2"
2552   [(set (match_operand:DI 0 "register_operand" "=r,r")
2553         (unspec:DI [(match_operand:DF 1 "nonimmediate_operand" "x,m")]
2554                    UNSPEC_FIX_NOTRUNC))]
2555   "TARGET_SSE2 && TARGET_64BIT"
2556   "%vcvtsd2siq\t{%1, %0|%0, %1}"
2557   [(set_attr "type" "sseicvt")
2558    (set_attr "athlon_decode" "double,vector")
2559    (set_attr "amdfam10_decode" "double,double")
2560    (set_attr "prefix_rep" "1")
2561    (set_attr "prefix" "maybe_vex")
2562    (set_attr "mode" "DI")])
2563
2564 (define_insn "sse2_cvttsd2si"
2565   [(set (match_operand:SI 0 "register_operand" "=r,r")
2566         (fix:SI
2567           (vec_select:DF
2568             (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2569             (parallel [(const_int 0)]))))]
2570   "TARGET_SSE2"
2571   "%vcvttsd2si\t{%1, %0|%0, %1}"
2572   [(set_attr "type" "sseicvt")
2573    (set_attr "prefix_rep" "1")
2574    (set_attr "prefix" "maybe_vex")
2575    (set_attr "mode" "SI")
2576    (set_attr "athlon_decode" "double,vector")
2577    (set_attr "amdfam10_decode" "double,double")])
2578
2579 (define_insn "sse2_cvttsd2siq"
2580   [(set (match_operand:DI 0 "register_operand" "=r,r")
2581         (fix:DI
2582           (vec_select:DF
2583             (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2584             (parallel [(const_int 0)]))))]
2585   "TARGET_SSE2 && TARGET_64BIT"
2586   "%vcvttsd2siq\t{%1, %0|%0, %1}"
2587   [(set_attr "type" "sseicvt")
2588    (set_attr "prefix_rep" "1")
2589    (set_attr "prefix" "maybe_vex")
2590    (set_attr "mode" "DI")
2591    (set_attr "athlon_decode" "double,vector")
2592    (set_attr "amdfam10_decode" "double,double")])
2593
2594 (define_insn "avx_cvtdq2pd256"
2595   [(set (match_operand:V4DF 0 "register_operand" "=x")
2596         (float:V4DF (match_operand:V4SI 1 "nonimmediate_operand" "xm")))]
2597   "TARGET_AVX"
2598   "vcvtdq2pd\t{%1, %0|%0, %1}"
2599   [(set_attr "type" "ssecvt")
2600    (set_attr "prefix" "vex")
2601    (set_attr "mode" "V4DF")])
2602
2603 (define_insn "sse2_cvtdq2pd"
2604   [(set (match_operand:V2DF 0 "register_operand" "=x")
2605         (float:V2DF
2606           (vec_select:V2SI
2607             (match_operand:V4SI 1 "nonimmediate_operand" "xm")
2608             (parallel [(const_int 0) (const_int 1)]))))]
2609   "TARGET_SSE2"
2610   "%vcvtdq2pd\t{%1, %0|%0, %1}"
2611   [(set_attr "type" "ssecvt")
2612    (set_attr "prefix" "maybe_vex")
2613    (set_attr "mode" "V2DF")])
2614
2615 (define_insn "avx_cvtpd2dq256"
2616   [(set (match_operand:V4SI 0 "register_operand" "=x")
2617         (unspec:V4SI [(match_operand:V4DF 1 "nonimmediate_operand" "xm")]
2618                      UNSPEC_FIX_NOTRUNC))]
2619   "TARGET_AVX"
2620   "vcvtpd2dq{y}\t{%1, %0|%0, %1}"
2621   [(set_attr "type" "ssecvt")
2622    (set_attr "prefix" "vex")
2623    (set_attr "mode" "OI")])
2624
2625 (define_expand "sse2_cvtpd2dq"
2626   [(set (match_operand:V4SI 0 "register_operand" "")
2627         (vec_concat:V4SI
2628           (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "")]
2629                        UNSPEC_FIX_NOTRUNC)
2630           (match_dup 2)))]
2631   "TARGET_SSE2"
2632   "operands[2] = CONST0_RTX (V2SImode);")
2633
2634 (define_insn "*sse2_cvtpd2dq"
2635   [(set (match_operand:V4SI 0 "register_operand" "=x")
2636         (vec_concat:V4SI
2637           (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
2638                        UNSPEC_FIX_NOTRUNC)
2639           (match_operand:V2SI 2 "const0_operand" "")))]
2640   "TARGET_SSE2"
2641   "* return TARGET_AVX ? \"vcvtpd2dq{x}\t{%1, %0|%0, %1}\"
2642                        : \"cvtpd2dq\t{%1, %0|%0, %1}\";"
2643   [(set_attr "type" "ssecvt")
2644    (set_attr "prefix_rep" "1")
2645    (set_attr "prefix" "maybe_vex")
2646    (set_attr "mode" "TI")
2647    (set_attr "amdfam10_decode" "double")])
2648
2649 (define_insn "avx_cvttpd2dq256"
2650   [(set (match_operand:V4SI 0 "register_operand" "=x")
2651         (fix:V4SI (match_operand:V4DF 1 "nonimmediate_operand" "xm")))]
2652   "TARGET_AVX"
2653   "vcvttpd2dq{y}\t{%1, %0|%0, %1}"
2654   [(set_attr "type" "ssecvt")
2655    (set_attr "prefix" "vex")
2656    (set_attr "mode" "OI")])
2657
2658 (define_expand "sse2_cvttpd2dq"
2659   [(set (match_operand:V4SI 0 "register_operand" "")
2660         (vec_concat:V4SI
2661           (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" ""))
2662           (match_dup 2)))]
2663   "TARGET_SSE2"
2664   "operands[2] = CONST0_RTX (V2SImode);")
2665
2666 (define_insn "*sse2_cvttpd2dq"
2667   [(set (match_operand:V4SI 0 "register_operand" "=x")
2668         (vec_concat:V4SI
2669           (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm"))
2670           (match_operand:V2SI 2 "const0_operand" "")))]
2671   "TARGET_SSE2"
2672   "* return TARGET_AVX ? \"vcvttpd2dq{x}\t{%1, %0|%0, %1}\"
2673                        : \"cvttpd2dq\t{%1, %0|%0, %1}\";"
2674   [(set_attr "type" "ssecvt")
2675    (set_attr "prefix_rep" "1")
2676    (set_attr "prefix" "maybe_vex")
2677    (set_attr "mode" "TI")
2678    (set_attr "amdfam10_decode" "double")])
2679
2680 (define_insn "*avx_cvtsd2ss"
2681   [(set (match_operand:V4SF 0 "register_operand" "=x")
2682         (vec_merge:V4SF
2683           (vec_duplicate:V4SF
2684             (float_truncate:V2SF
2685               (match_operand:V2DF 2 "nonimmediate_operand" "xm")))
2686           (match_operand:V4SF 1 "register_operand" "x")
2687           (const_int 1)))]
2688   "TARGET_AVX"
2689   "vcvtsd2ss\t{%2, %1, %0|%0, %1, %2}"
2690   [(set_attr "type" "ssecvt")
2691    (set_attr "prefix" "vex")
2692    (set_attr "mode" "SF")])
2693
2694 (define_insn "sse2_cvtsd2ss"
2695   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
2696         (vec_merge:V4SF
2697           (vec_duplicate:V4SF
2698             (float_truncate:V2SF
2699               (match_operand:V2DF 2 "nonimmediate_operand" "x,m")))
2700           (match_operand:V4SF 1 "register_operand" "0,0")
2701           (const_int 1)))]
2702   "TARGET_SSE2"
2703   "cvtsd2ss\t{%2, %0|%0, %2}"
2704   [(set_attr "type" "ssecvt")
2705    (set_attr "athlon_decode" "vector,double")
2706    (set_attr "amdfam10_decode" "vector,double")
2707    (set_attr "mode" "SF")])
2708
2709 (define_insn "*avx_cvtss2sd"
2710   [(set (match_operand:V2DF 0 "register_operand" "=x")
2711         (vec_merge:V2DF
2712           (float_extend:V2DF
2713             (vec_select:V2SF
2714               (match_operand:V4SF 2 "nonimmediate_operand" "xm")
2715               (parallel [(const_int 0) (const_int 1)])))
2716           (match_operand:V2DF 1 "register_operand" "x")
2717           (const_int 1)))]
2718   "TARGET_AVX"
2719   "vcvtss2sd\t{%2, %1, %0|%0, %1, %2}"
2720   [(set_attr "type" "ssecvt")
2721    (set_attr "prefix" "vex")
2722    (set_attr "mode" "DF")])
2723
2724 (define_insn "sse2_cvtss2sd"
2725   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
2726         (vec_merge:V2DF
2727           (float_extend:V2DF
2728             (vec_select:V2SF
2729               (match_operand:V4SF 2 "nonimmediate_operand" "x,m")
2730               (parallel [(const_int 0) (const_int 1)])))
2731           (match_operand:V2DF 1 "register_operand" "0,0")
2732           (const_int 1)))]
2733   "TARGET_SSE2"
2734   "cvtss2sd\t{%2, %0|%0, %2}"
2735   [(set_attr "type" "ssecvt")
2736    (set_attr "amdfam10_decode" "vector,double")
2737    (set_attr "mode" "DF")])
2738
2739 (define_insn "avx_cvtpd2ps256"
2740   [(set (match_operand:V4SF 0 "register_operand" "=x")
2741         (float_truncate:V4SF
2742           (match_operand:V4DF 1 "nonimmediate_operand" "xm")))]
2743   "TARGET_AVX"
2744   "vcvtpd2ps{y}\t{%1, %0|%0, %1}"
2745   [(set_attr "type" "ssecvt")
2746    (set_attr "prefix" "vex")
2747    (set_attr "mode" "V4SF")])
2748
2749 (define_expand "sse2_cvtpd2ps"
2750   [(set (match_operand:V4SF 0 "register_operand" "")
2751         (vec_concat:V4SF
2752           (float_truncate:V2SF
2753             (match_operand:V2DF 1 "nonimmediate_operand" ""))
2754           (match_dup 2)))]
2755   "TARGET_SSE2"
2756   "operands[2] = CONST0_RTX (V2SFmode);")
2757
2758 (define_insn "*sse2_cvtpd2ps"
2759   [(set (match_operand:V4SF 0 "register_operand" "=x")
2760         (vec_concat:V4SF
2761           (float_truncate:V2SF
2762             (match_operand:V2DF 1 "nonimmediate_operand" "xm"))
2763           (match_operand:V2SF 2 "const0_operand" "")))]
2764   "TARGET_SSE2"
2765   "* return TARGET_AVX ? \"vcvtpd2ps{x}\t{%1, %0|%0, %1}\"
2766                        : \"cvtpd2ps\t{%1, %0|%0, %1}\";"
2767   [(set_attr "type" "ssecvt")
2768    (set_attr "prefix_data16" "1")
2769    (set_attr "prefix" "maybe_vex")
2770    (set_attr "mode" "V4SF")
2771    (set_attr "amdfam10_decode" "double")])
2772
2773 (define_insn "avx_cvtps2pd256"
2774   [(set (match_operand:V4DF 0 "register_operand" "=x")
2775         (float_extend:V4DF
2776           (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
2777   "TARGET_AVX"
2778   "vcvtps2pd\t{%1, %0|%0, %1}"
2779   [(set_attr "type" "ssecvt")
2780    (set_attr "prefix" "vex")
2781    (set_attr "mode" "V4DF")])
2782
2783 (define_insn "sse2_cvtps2pd"
2784   [(set (match_operand:V2DF 0 "register_operand" "=x")
2785         (float_extend:V2DF
2786           (vec_select:V2SF
2787             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
2788             (parallel [(const_int 0) (const_int 1)]))))]
2789   "TARGET_SSE2"
2790   "%vcvtps2pd\t{%1, %0|%0, %1}"
2791   [(set_attr "type" "ssecvt")
2792    (set_attr "prefix" "maybe_vex")
2793    (set_attr "mode" "V2DF")
2794    (set_attr "amdfam10_decode" "direct")])
2795
2796 (define_expand "vec_unpacks_hi_v4sf"
2797   [(set (match_dup 2)
2798    (vec_select:V4SF
2799      (vec_concat:V8SF
2800        (match_dup 2)
2801        (match_operand:V4SF 1 "nonimmediate_operand" ""))
2802      (parallel [(const_int 6)
2803                 (const_int 7)
2804                 (const_int 2)
2805                 (const_int 3)])))
2806   (set (match_operand:V2DF 0 "register_operand" "")
2807    (float_extend:V2DF
2808      (vec_select:V2SF
2809        (match_dup 2)
2810        (parallel [(const_int 0) (const_int 1)]))))]
2811  "TARGET_SSE2"
2812 {
2813  operands[2] = gen_reg_rtx (V4SFmode);
2814 })
2815
2816 (define_expand "vec_unpacks_lo_v4sf"
2817   [(set (match_operand:V2DF 0 "register_operand" "")
2818         (float_extend:V2DF
2819           (vec_select:V2SF
2820             (match_operand:V4SF 1 "nonimmediate_operand" "")
2821             (parallel [(const_int 0) (const_int 1)]))))]
2822   "TARGET_SSE2")
2823
2824 (define_expand "vec_unpacks_float_hi_v8hi"
2825   [(match_operand:V4SF 0 "register_operand" "")
2826    (match_operand:V8HI 1 "register_operand" "")]
2827   "TARGET_SSE2"
2828 {
2829   rtx tmp = gen_reg_rtx (V4SImode);
2830
2831   emit_insn (gen_vec_unpacks_hi_v8hi (tmp, operands[1]));
2832   emit_insn (gen_sse2_cvtdq2ps (operands[0], tmp));
2833   DONE;
2834 })
2835
2836 (define_expand "vec_unpacks_float_lo_v8hi"
2837   [(match_operand:V4SF 0 "register_operand" "")
2838    (match_operand:V8HI 1 "register_operand" "")]
2839   "TARGET_SSE2"
2840 {
2841   rtx tmp = gen_reg_rtx (V4SImode);
2842
2843   emit_insn (gen_vec_unpacks_lo_v8hi (tmp, operands[1]));
2844   emit_insn (gen_sse2_cvtdq2ps (operands[0], tmp));
2845   DONE;
2846 })
2847
2848 (define_expand "vec_unpacku_float_hi_v8hi"
2849   [(match_operand:V4SF 0 "register_operand" "")
2850    (match_operand:V8HI 1 "register_operand" "")]
2851   "TARGET_SSE2"
2852 {
2853   rtx tmp = gen_reg_rtx (V4SImode);
2854
2855   emit_insn (gen_vec_unpacku_hi_v8hi (tmp, operands[1]));
2856   emit_insn (gen_sse2_cvtdq2ps (operands[0], tmp));
2857   DONE;
2858 })
2859
2860 (define_expand "vec_unpacku_float_lo_v8hi"
2861   [(match_operand:V4SF 0 "register_operand" "")
2862    (match_operand:V8HI 1 "register_operand" "")]
2863   "TARGET_SSE2"
2864 {
2865   rtx tmp = gen_reg_rtx (V4SImode);
2866
2867   emit_insn (gen_vec_unpacku_lo_v8hi (tmp, operands[1]));
2868   emit_insn (gen_sse2_cvtdq2ps (operands[0], tmp));
2869   DONE;
2870 })
2871
2872 (define_expand "vec_unpacks_float_hi_v4si"
2873   [(set (match_dup 2)
2874         (vec_select:V4SI
2875           (match_operand:V4SI 1 "nonimmediate_operand" "")
2876           (parallel [(const_int 2)
2877                      (const_int 3)
2878                      (const_int 2)
2879                      (const_int 3)])))
2880    (set (match_operand:V2DF 0 "register_operand" "")
2881         (float:V2DF
2882           (vec_select:V2SI
2883           (match_dup 2)
2884             (parallel [(const_int 0) (const_int 1)]))))]
2885  "TARGET_SSE2"
2886 {
2887  operands[2] = gen_reg_rtx (V4SImode);
2888 })
2889
2890 (define_expand "vec_unpacks_float_lo_v4si"
2891   [(set (match_operand:V2DF 0 "register_operand" "")
2892         (float:V2DF
2893           (vec_select:V2SI
2894             (match_operand:V4SI 1 "nonimmediate_operand" "")
2895             (parallel [(const_int 0) (const_int 1)]))))]
2896   "TARGET_SSE2")
2897
2898 (define_expand "vec_pack_trunc_v2df"
2899   [(match_operand:V4SF 0 "register_operand" "")
2900    (match_operand:V2DF 1 "nonimmediate_operand" "")
2901    (match_operand:V2DF 2 "nonimmediate_operand" "")]
2902   "TARGET_SSE2"
2903 {
2904   rtx r1, r2;
2905
2906   r1 = gen_reg_rtx (V4SFmode);
2907   r2 = gen_reg_rtx (V4SFmode);
2908
2909   emit_insn (gen_sse2_cvtpd2ps (r1, operands[1]));
2910   emit_insn (gen_sse2_cvtpd2ps (r2, operands[2]));
2911   emit_insn (gen_sse_movlhps (operands[0], r1, r2));
2912   DONE;
2913 })
2914
2915 (define_expand "vec_pack_sfix_trunc_v2df"
2916   [(match_operand:V4SI 0 "register_operand" "")
2917    (match_operand:V2DF 1 "nonimmediate_operand" "")
2918    (match_operand:V2DF 2 "nonimmediate_operand" "")]
2919   "TARGET_SSE2"
2920 {
2921   rtx r1, r2;
2922
2923   r1 = gen_reg_rtx (V4SImode);
2924   r2 = gen_reg_rtx (V4SImode);
2925
2926   emit_insn (gen_sse2_cvttpd2dq (r1, operands[1]));
2927   emit_insn (gen_sse2_cvttpd2dq (r2, operands[2]));
2928   emit_insn (gen_sse2_punpcklqdq (gen_lowpart (V2DImode, operands[0]),
2929                                   gen_lowpart (V2DImode, r1),
2930                                   gen_lowpart (V2DImode, r2)));
2931   DONE;
2932 })
2933
2934 (define_expand "vec_pack_sfix_v2df"
2935   [(match_operand:V4SI 0 "register_operand" "")
2936    (match_operand:V2DF 1 "nonimmediate_operand" "")
2937    (match_operand:V2DF 2 "nonimmediate_operand" "")]
2938   "TARGET_SSE2"
2939 {
2940   rtx r1, r2;
2941
2942   r1 = gen_reg_rtx (V4SImode);
2943   r2 = gen_reg_rtx (V4SImode);
2944
2945   emit_insn (gen_sse2_cvtpd2dq (r1, operands[1]));
2946   emit_insn (gen_sse2_cvtpd2dq (r2, operands[2]));
2947   emit_insn (gen_sse2_punpcklqdq (gen_lowpart (V2DImode, operands[0]),
2948                                   gen_lowpart (V2DImode, r1),
2949                                   gen_lowpart (V2DImode, r2)));
2950   DONE;
2951 })
2952
2953 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2954 ;;
2955 ;; Parallel single-precision floating point element swizzling
2956 ;;
2957 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2958
2959 (define_expand "sse_movhlps_exp"
2960   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
2961         (vec_select:V4SF
2962           (vec_concat:V8SF
2963             (match_operand:V4SF 1 "nonimmediate_operand" "")
2964             (match_operand:V4SF 2 "nonimmediate_operand" ""))
2965           (parallel [(const_int 6)
2966                      (const_int 7)
2967                      (const_int 2)
2968                      (const_int 3)])))]
2969   "TARGET_SSE"
2970   "ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);")
2971
2972 (define_insn "*avx_movhlps"
2973   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,m")
2974         (vec_select:V4SF
2975           (vec_concat:V8SF
2976             (match_operand:V4SF 1 "nonimmediate_operand" " x,x,0")
2977             (match_operand:V4SF 2 "nonimmediate_operand" " x,o,x"))
2978           (parallel [(const_int 6)
2979                      (const_int 7)
2980                      (const_int 2)
2981                      (const_int 3)])))]
2982   "TARGET_AVX && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
2983   "@
2984    vmovhlps\t{%2, %1, %0|%0, %1, %2}
2985    vmovlps\t{%H2, %1, %0|%0, %1, %H2}
2986    vmovhps\t{%2, %0|%0, %2}"
2987   [(set_attr "type" "ssemov")
2988    (set_attr "prefix" "vex")
2989    (set_attr "mode" "V4SF,V2SF,V2SF")])
2990
2991 (define_insn "sse_movhlps"
2992   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,m")
2993         (vec_select:V4SF
2994           (vec_concat:V8SF
2995             (match_operand:V4SF 1 "nonimmediate_operand" " 0,0,0")
2996             (match_operand:V4SF 2 "nonimmediate_operand" " x,o,x"))
2997           (parallel [(const_int 6)
2998                      (const_int 7)
2999                      (const_int 2)
3000                      (const_int 3)])))]
3001   "TARGET_SSE && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
3002   "@
3003    movhlps\t{%2, %0|%0, %2}
3004    movlps\t{%H2, %0|%0, %H2}
3005    movhps\t{%2, %0|%0, %2}"
3006   [(set_attr "type" "ssemov")
3007    (set_attr "mode" "V4SF,V2SF,V2SF")])
3008
3009 (define_expand "sse_movlhps_exp"
3010   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3011         (vec_select:V4SF
3012           (vec_concat:V8SF
3013             (match_operand:V4SF 1 "nonimmediate_operand" "")
3014             (match_operand:V4SF 2 "nonimmediate_operand" ""))
3015           (parallel [(const_int 0)
3016                      (const_int 1)
3017                      (const_int 4)
3018                      (const_int 5)])))]
3019   "TARGET_SSE"
3020   "ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);")
3021
3022 (define_insn "*avx_movlhps"
3023   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,o")
3024         (vec_select:V4SF
3025           (vec_concat:V8SF
3026             (match_operand:V4SF 1 "nonimmediate_operand" " x,x,0")
3027             (match_operand:V4SF 2 "nonimmediate_operand" " x,m,x"))
3028           (parallel [(const_int 0)
3029                      (const_int 1)
3030                      (const_int 4)
3031                      (const_int 5)])))]
3032   "TARGET_AVX && ix86_binary_operator_ok (UNKNOWN, V4SFmode, operands)"
3033   "@
3034    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3035    vmovhps\t{%2, %1, %0|%0, %1, %2}
3036    vmovlps\t{%2, %H0|%H0, %2}"
3037   [(set_attr "type" "ssemov")
3038    (set_attr "prefix" "vex")
3039    (set_attr "mode" "V4SF,V2SF,V2SF")])
3040
3041 (define_insn "sse_movlhps"
3042   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,o")
3043         (vec_select:V4SF
3044           (vec_concat:V8SF
3045             (match_operand:V4SF 1 "nonimmediate_operand" " 0,0,0")
3046             (match_operand:V4SF 2 "nonimmediate_operand" " x,m,x"))
3047           (parallel [(const_int 0)
3048                      (const_int 1)
3049                      (const_int 4)
3050                      (const_int 5)])))]
3051   "TARGET_SSE && ix86_binary_operator_ok (UNKNOWN, V4SFmode, operands)"
3052   "@
3053    movlhps\t{%2, %0|%0, %2}
3054    movhps\t{%2, %0|%0, %2}
3055    movlps\t{%2, %H0|%H0, %2}"
3056   [(set_attr "type" "ssemov")
3057    (set_attr "mode" "V4SF,V2SF,V2SF")])
3058
3059 (define_insn "avx_unpckhps256"
3060   [(set (match_operand:V8SF 0 "register_operand" "=x")
3061         (vec_select:V8SF
3062           (vec_concat:V16SF
3063             (match_operand:V8SF 1 "register_operand" "x")
3064             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3065           (parallel [(const_int 2) (const_int 10)
3066                      (const_int 3) (const_int 11)
3067                      (const_int 6) (const_int 14)
3068                      (const_int 7) (const_int 15)])))]
3069   "TARGET_AVX"
3070   "vunpckhps\t{%2, %1, %0|%0, %1, %2}"
3071   [(set_attr "type" "sselog")
3072    (set_attr "prefix" "vex")
3073    (set_attr "mode" "V8SF")])
3074
3075 (define_insn "*avx_unpckhps"
3076   [(set (match_operand:V4SF 0 "register_operand" "=x")
3077         (vec_select:V4SF
3078           (vec_concat:V8SF
3079             (match_operand:V4SF 1 "register_operand" "x")
3080             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
3081           (parallel [(const_int 2) (const_int 6)
3082                      (const_int 3) (const_int 7)])))]
3083   "TARGET_AVX"
3084   "vunpckhps\t{%2, %1, %0|%0, %1, %2}"
3085   [(set_attr "type" "sselog")
3086    (set_attr "prefix" "vex")
3087    (set_attr "mode" "V4SF")])
3088
3089 (define_insn "sse_unpckhps"
3090   [(set (match_operand:V4SF 0 "register_operand" "=x")
3091         (vec_select:V4SF
3092           (vec_concat:V8SF
3093             (match_operand:V4SF 1 "register_operand" "0")
3094             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
3095           (parallel [(const_int 2) (const_int 6)
3096                      (const_int 3) (const_int 7)])))]
3097   "TARGET_SSE"
3098   "unpckhps\t{%2, %0|%0, %2}"
3099   [(set_attr "type" "sselog")
3100    (set_attr "mode" "V4SF")])
3101
3102 (define_insn "avx_unpcklps256"
3103   [(set (match_operand:V8SF 0 "register_operand" "=x")
3104         (vec_select:V8SF
3105           (vec_concat:V16SF
3106             (match_operand:V8SF 1 "register_operand" "x")
3107             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3108           (parallel [(const_int 0) (const_int 8)
3109                      (const_int 1) (const_int 9)
3110                      (const_int 4) (const_int 12)
3111                      (const_int 5) (const_int 13)])))]
3112   "TARGET_AVX"
3113   "vunpcklps\t{%2, %1, %0|%0, %1, %2}"
3114   [(set_attr "type" "sselog")
3115    (set_attr "prefix" "vex")
3116    (set_attr "mode" "V8SF")])
3117
3118 (define_insn "*avx_unpcklps"
3119   [(set (match_operand:V4SF 0 "register_operand" "=x")
3120         (vec_select:V4SF
3121           (vec_concat:V8SF
3122             (match_operand:V4SF 1 "register_operand" "x")
3123             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
3124           (parallel [(const_int 0) (const_int 4)
3125                      (const_int 1) (const_int 5)])))]
3126   "TARGET_AVX"
3127   "vunpcklps\t{%2, %1, %0|%0, %1, %2}"
3128   [(set_attr "type" "sselog")
3129    (set_attr "prefix" "vex")
3130    (set_attr "mode" "V4SF")])
3131
3132 (define_insn "sse_unpcklps"
3133   [(set (match_operand:V4SF 0 "register_operand" "=x")
3134         (vec_select:V4SF
3135           (vec_concat:V8SF
3136             (match_operand:V4SF 1 "register_operand" "0")
3137             (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
3138           (parallel [(const_int 0) (const_int 4)
3139                      (const_int 1) (const_int 5)])))]
3140   "TARGET_SSE"
3141   "unpcklps\t{%2, %0|%0, %2}"
3142   [(set_attr "type" "sselog")
3143    (set_attr "mode" "V4SF")])
3144
3145 ;; These are modeled with the same vec_concat as the others so that we
3146 ;; capture users of shufps that can use the new instructions
3147 (define_insn "avx_movshdup256"
3148   [(set (match_operand:V8SF 0 "register_operand" "=x")
3149         (vec_select:V8SF
3150           (vec_concat:V16SF
3151             (match_operand:V8SF 1 "nonimmediate_operand" "xm")
3152             (match_dup 1))
3153           (parallel [(const_int 1) (const_int 1)
3154                      (const_int 3) (const_int 3)
3155                      (const_int 5) (const_int 5)
3156                      (const_int 7) (const_int 7)])))]
3157   "TARGET_AVX"
3158   "vmovshdup\t{%1, %0|%0, %1}"
3159   [(set_attr "type" "sse")
3160    (set_attr "prefix" "vex")
3161    (set_attr "mode" "V8SF")])
3162
3163 (define_insn "sse3_movshdup"
3164   [(set (match_operand:V4SF 0 "register_operand" "=x")
3165         (vec_select:V4SF
3166           (vec_concat:V8SF
3167             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
3168             (match_dup 1))
3169           (parallel [(const_int 1)
3170                      (const_int 1)
3171                      (const_int 7)
3172                      (const_int 7)])))]
3173   "TARGET_SSE3"
3174   "%vmovshdup\t{%1, %0|%0, %1}"
3175   [(set_attr "type" "sse")
3176    (set_attr "prefix_rep" "1")
3177    (set_attr "prefix" "maybe_vex")
3178    (set_attr "mode" "V4SF")])
3179
3180 (define_insn "avx_movsldup256"
3181   [(set (match_operand:V8SF 0 "register_operand" "=x")
3182         (vec_select:V8SF
3183           (vec_concat:V16SF
3184             (match_operand:V8SF 1 "nonimmediate_operand" "xm")
3185             (match_dup 1))
3186           (parallel [(const_int 0) (const_int 0)
3187                      (const_int 2) (const_int 2)
3188                      (const_int 4) (const_int 4)
3189                      (const_int 6) (const_int 6)])))]
3190   "TARGET_AVX"
3191   "vmovsldup\t{%1, %0|%0, %1}"
3192   [(set_attr "type" "sse")
3193    (set_attr "prefix" "vex")
3194    (set_attr "mode" "V8SF")])
3195
3196 (define_insn "sse3_movsldup"
3197   [(set (match_operand:V4SF 0 "register_operand" "=x")
3198         (vec_select:V4SF
3199           (vec_concat:V8SF
3200             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
3201             (match_dup 1))
3202           (parallel [(const_int 0)
3203                      (const_int 0)
3204                      (const_int 6)
3205                      (const_int 6)])))]
3206   "TARGET_SSE3"
3207   "%vmovsldup\t{%1, %0|%0, %1}"
3208   [(set_attr "type" "sse")
3209    (set_attr "prefix_rep" "1")
3210    (set_attr "prefix" "maybe_vex")
3211    (set_attr "mode" "V4SF")])
3212
3213 (define_expand "avx_shufps256"
3214   [(match_operand:V8SF 0 "register_operand" "")
3215    (match_operand:V8SF 1 "register_operand" "")
3216    (match_operand:V8SF 2 "nonimmediate_operand" "")
3217    (match_operand:SI 3 "const_int_operand" "")]
3218   "TARGET_AVX"
3219 {
3220   int mask = INTVAL (operands[3]);
3221   emit_insn (gen_avx_shufps256_1 (operands[0], operands[1], operands[2],
3222                                   GEN_INT ((mask >> 0) & 3),
3223                                   GEN_INT ((mask >> 2) & 3),
3224                                   GEN_INT (((mask >> 4) & 3) + 8),
3225                                   GEN_INT (((mask >> 6) & 3) + 8),
3226                                   GEN_INT (((mask >> 0) & 3) + 4),
3227                                   GEN_INT (((mask >> 2) & 3) + 4),
3228                                   GEN_INT (((mask >> 4) & 3) + 12),
3229                                   GEN_INT (((mask >> 6) & 3) + 12)));
3230   DONE;
3231 })
3232
3233 ;; One bit in mask selects 2 elements.
3234 (define_insn "avx_shufps256_1"
3235   [(set (match_operand:V8SF 0 "register_operand" "=x")
3236         (vec_select:V8SF
3237           (vec_concat:V16SF
3238             (match_operand:V8SF 1 "register_operand" "x")
3239             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3240           (parallel [(match_operand 3  "const_0_to_3_operand"   "")
3241                      (match_operand 4  "const_0_to_3_operand"   "")
3242                      (match_operand 5  "const_8_to_11_operand"  "")
3243                      (match_operand 6  "const_8_to_11_operand"  "")
3244                      (match_operand 7  "const_4_to_7_operand"   "")
3245                      (match_operand 8  "const_4_to_7_operand"   "")
3246                      (match_operand 9  "const_12_to_15_operand" "")
3247                      (match_operand 10 "const_12_to_15_operand" "")])))]
3248   "TARGET_AVX
3249    && (INTVAL (operands[3]) == (INTVAL (operands[7]) - 4)
3250        && INTVAL (operands[4]) == (INTVAL (operands[8]) - 4)
3251        && INTVAL (operands[5]) == (INTVAL (operands[9]) - 4)
3252        && INTVAL (operands[6]) == (INTVAL (operands[10]) - 4))"
3253 {
3254   int mask;
3255   mask = INTVAL (operands[3]);
3256   mask |= INTVAL (operands[4]) << 2;
3257   mask |= (INTVAL (operands[5]) - 8) << 4;
3258   mask |= (INTVAL (operands[6]) - 8) << 6;
3259   operands[3] = GEN_INT (mask);
3260
3261   return "vshufps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3262 }
3263   [(set_attr "type" "sselog")
3264    (set_attr "prefix" "vex")
3265    (set_attr "mode" "V8SF")])
3266
3267 (define_expand "sse_shufps"
3268   [(match_operand:V4SF 0 "register_operand" "")
3269    (match_operand:V4SF 1 "register_operand" "")
3270    (match_operand:V4SF 2 "nonimmediate_operand" "")
3271    (match_operand:SI 3 "const_int_operand" "")]
3272   "TARGET_SSE"
3273 {
3274   int mask = INTVAL (operands[3]);
3275   emit_insn (gen_sse_shufps_v4sf (operands[0], operands[1], operands[2],
3276                                GEN_INT ((mask >> 0) & 3),
3277                                GEN_INT ((mask >> 2) & 3),
3278                                GEN_INT (((mask >> 4) & 3) + 4),
3279                                GEN_INT (((mask >> 6) & 3) + 4)));
3280   DONE;
3281 })
3282
3283 (define_insn "*avx_shufps_<mode>"
3284   [(set (match_operand:SSEMODE4S 0 "register_operand" "=x")
3285         (vec_select:SSEMODE4S
3286           (vec_concat:<ssedoublesizemode>
3287             (match_operand:SSEMODE4S 1 "register_operand" "x")
3288             (match_operand:SSEMODE4S 2 "nonimmediate_operand" "xm"))
3289           (parallel [(match_operand 3 "const_0_to_3_operand" "")
3290                      (match_operand 4 "const_0_to_3_operand" "")
3291                      (match_operand 5 "const_4_to_7_operand" "")
3292                      (match_operand 6 "const_4_to_7_operand" "")])))]
3293   "TARGET_AVX"
3294 {
3295   int mask = 0;
3296   mask |= INTVAL (operands[3]) << 0;
3297   mask |= INTVAL (operands[4]) << 2;
3298   mask |= (INTVAL (operands[5]) - 4) << 4;
3299   mask |= (INTVAL (operands[6]) - 4) << 6;
3300   operands[3] = GEN_INT (mask);
3301
3302   return "vshufps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3303 }
3304   [(set_attr "type" "sselog")
3305    (set_attr "prefix" "vex")
3306    (set_attr "mode" "V4SF")])
3307
3308 (define_insn "sse_shufps_<mode>"
3309   [(set (match_operand:SSEMODE4S 0 "register_operand" "=x")
3310         (vec_select:SSEMODE4S
3311           (vec_concat:<ssedoublesizemode>
3312             (match_operand:SSEMODE4S 1 "register_operand" "0")
3313             (match_operand:SSEMODE4S 2 "nonimmediate_operand" "xm"))
3314           (parallel [(match_operand 3 "const_0_to_3_operand" "")
3315                      (match_operand 4 "const_0_to_3_operand" "")
3316                      (match_operand 5 "const_4_to_7_operand" "")
3317                      (match_operand 6 "const_4_to_7_operand" "")])))]
3318   "TARGET_SSE"
3319 {
3320   int mask = 0;
3321   mask |= INTVAL (operands[3]) << 0;
3322   mask |= INTVAL (operands[4]) << 2;
3323   mask |= (INTVAL (operands[5]) - 4) << 4;
3324   mask |= (INTVAL (operands[6]) - 4) << 6;
3325   operands[3] = GEN_INT (mask);
3326
3327   return "shufps\t{%3, %2, %0|%0, %2, %3}";
3328 }
3329   [(set_attr "type" "sselog")
3330    (set_attr "mode" "V4SF")])
3331
3332 (define_insn "sse_storehps"
3333   [(set (match_operand:V2SF 0 "nonimmediate_operand" "=m,x,x")
3334         (vec_select:V2SF
3335           (match_operand:V4SF 1 "nonimmediate_operand" "x,x,o")
3336           (parallel [(const_int 2) (const_int 3)])))]
3337   "TARGET_SSE"
3338   "@
3339    %vmovhps\t{%1, %0|%0, %1}
3340    %vmovhlps\t{%1, %d0|%d0, %1}
3341    %vmovlps\t{%H1, %d0|%d0, %H1}"
3342   [(set_attr "type" "ssemov")
3343    (set_attr "prefix" "maybe_vex")
3344    (set_attr "mode" "V2SF,V4SF,V2SF")])
3345
3346 (define_expand "sse_loadhps_exp"
3347   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3348         (vec_concat:V4SF
3349           (vec_select:V2SF
3350             (match_operand:V4SF 1 "nonimmediate_operand" "")
3351             (parallel [(const_int 0) (const_int 1)]))
3352           (match_operand:V2SF 2 "nonimmediate_operand" "")))]
3353   "TARGET_SSE"
3354   "ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);")
3355
3356 (define_insn "*avx_loadhps"
3357   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,x,o")
3358         (vec_concat:V4SF
3359           (vec_select:V2SF
3360             (match_operand:V4SF 1 "nonimmediate_operand" "x,x,0")
3361             (parallel [(const_int 0) (const_int 1)]))
3362           (match_operand:V2SF 2 "nonimmediate_operand" "m,x,x")))]
3363   "TARGET_AVX"
3364   "@
3365    vmovhps\t{%2, %1, %0|%0, %1, %2}
3366    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3367    vmovlps\t{%2, %H0|%H0, %2}"
3368   [(set_attr "type" "ssemov")
3369    (set_attr "prefix" "vex")
3370    (set_attr "mode" "V2SF,V4SF,V2SF")])
3371
3372 (define_insn "sse_loadhps"
3373   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,x,o")
3374         (vec_concat:V4SF
3375           (vec_select:V2SF
3376             (match_operand:V4SF 1 "nonimmediate_operand" "0,0,0")
3377             (parallel [(const_int 0) (const_int 1)]))
3378           (match_operand:V2SF 2 "nonimmediate_operand" "m,x,x")))]
3379   "TARGET_SSE"
3380   "@
3381    movhps\t{%2, %0|%0, %2}
3382    movlhps\t{%2, %0|%0, %2}
3383    movlps\t{%2, %H0|%H0, %2}"
3384   [(set_attr "type" "ssemov")
3385    (set_attr "mode" "V2SF,V4SF,V2SF")])
3386
3387 (define_insn "*avx_storelps"
3388   [(set (match_operand:V2SF 0 "nonimmediate_operand" "=m,x,x")
3389         (vec_select:V2SF
3390           (match_operand:V4SF 1 "nonimmediate_operand" "x,x,m")
3391           (parallel [(const_int 0) (const_int 1)])))]
3392   "TARGET_AVX"
3393   "@
3394    vmovlps\t{%1, %0|%0, %1}
3395    vmovaps\t{%1, %0|%0, %1}
3396    vmovlps\t{%1, %0, %0|%0, %0, %1}"
3397   [(set_attr "type" "ssemov")
3398    (set_attr "prefix" "vex")
3399    (set_attr "mode" "V2SF,V2DF,V2SF")])
3400
3401 (define_insn "sse_storelps"
3402   [(set (match_operand:V2SF 0 "nonimmediate_operand" "=m,x,x")
3403         (vec_select:V2SF
3404           (match_operand:V4SF 1 "nonimmediate_operand" "x,x,m")
3405           (parallel [(const_int 0) (const_int 1)])))]
3406   "TARGET_SSE"
3407   "@
3408    movlps\t{%1, %0|%0, %1}
3409    movaps\t{%1, %0|%0, %1}
3410    movlps\t{%1, %0|%0, %1}"
3411   [(set_attr "type" "ssemov")
3412    (set_attr "mode" "V2SF,V4SF,V2SF")])
3413
3414 (define_expand "sse_loadlps_exp"
3415   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3416         (vec_concat:V4SF
3417           (match_operand:V2SF 2 "nonimmediate_operand" "")
3418           (vec_select:V2SF
3419             (match_operand:V4SF 1 "nonimmediate_operand" "")
3420             (parallel [(const_int 2) (const_int 3)]))))]
3421   "TARGET_SSE"
3422   "ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);")
3423
3424 (define_insn "*avx_loadlps"
3425   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,x,m")
3426         (vec_concat:V4SF
3427           (match_operand:V2SF 2 "nonimmediate_operand" "x,m,x")
3428           (vec_select:V2SF
3429             (match_operand:V4SF 1 "nonimmediate_operand" "x,x,0")
3430             (parallel [(const_int 2) (const_int 3)]))))]
3431   "TARGET_AVX"
3432   "@
3433    shufps\t{$0xe4, %1, %2, %0|%0, %2, %1, 0xe4}
3434    vmovlps\t{%2, %1, %0|%0, %1, %2}
3435    vmovlps\t{%2, %0|%0, %2}"
3436   [(set_attr "type" "sselog,ssemov,ssemov")
3437    (set_attr "prefix" "vex")
3438    (set_attr "mode" "V4SF,V2SF,V2SF")])
3439
3440 (define_insn "sse_loadlps"
3441   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,x,m")
3442         (vec_concat:V4SF
3443           (match_operand:V2SF 2 "nonimmediate_operand" "0,m,x")
3444           (vec_select:V2SF
3445             (match_operand:V4SF 1 "nonimmediate_operand" "x,0,0")
3446             (parallel [(const_int 2) (const_int 3)]))))]
3447   "TARGET_SSE"
3448   "@
3449    shufps\t{$0xe4, %1, %0|%0, %1, 0xe4}
3450    movlps\t{%2, %0|%0, %2}
3451    movlps\t{%2, %0|%0, %2}"
3452   [(set_attr "type" "sselog,ssemov,ssemov")
3453    (set_attr "mode" "V4SF,V2SF,V2SF")])
3454
3455 (define_insn "*avx_movss"
3456   [(set (match_operand:V4SF 0 "register_operand" "=x")
3457         (vec_merge:V4SF
3458           (match_operand:V4SF 2 "register_operand" "x")
3459           (match_operand:V4SF 1 "register_operand" "x")
3460           (const_int 1)))]
3461   "TARGET_AVX"
3462   "vmovss\t{%2, %1, %0|%0, %1, %2}"
3463   [(set_attr "type" "ssemov")
3464    (set_attr "prefix" "vex")
3465    (set_attr "mode" "SF")])
3466
3467 (define_insn "sse_movss"
3468   [(set (match_operand:V4SF 0 "register_operand" "=x")
3469         (vec_merge:V4SF
3470           (match_operand:V4SF 2 "register_operand" "x")
3471           (match_operand:V4SF 1 "register_operand" "0")
3472           (const_int 1)))]
3473   "TARGET_SSE"
3474   "movss\t{%2, %0|%0, %2}"
3475   [(set_attr "type" "ssemov")
3476    (set_attr "mode" "SF")])
3477
3478 (define_insn "*vec_dupv4sf_avx"
3479   [(set (match_operand:V4SF 0 "register_operand" "=x")
3480         (vec_duplicate:V4SF
3481           (match_operand:SF 1 "register_operand" "x")))]
3482   "TARGET_AVX"
3483   "vshufps\t{$0, %1, %1, %0|%0, %1, %1, 0}"
3484   [(set_attr "type" "sselog1")
3485    (set_attr "prefix" "vex")
3486    (set_attr "mode" "V4SF")])
3487
3488 (define_insn "*vec_dupv4sf"
3489   [(set (match_operand:V4SF 0 "register_operand" "=x")
3490         (vec_duplicate:V4SF
3491           (match_operand:SF 1 "register_operand" "0")))]
3492   "TARGET_SSE"
3493   "shufps\t{$0, %0, %0|%0, %0, 0}"
3494   [(set_attr "type" "sselog1")
3495    (set_attr "mode" "V4SF")])
3496
3497 (define_insn "*vec_concatv2sf_avx"
3498   [(set (match_operand:V2SF 0 "register_operand"     "=x,x,x,*y ,*y")
3499         (vec_concat:V2SF
3500           (match_operand:SF 1 "nonimmediate_operand" " x,x,m, x , m")
3501           (match_operand:SF 2 "vector_move_operand"  " x,m,C,*ym, C")))]
3502   "TARGET_AVX"
3503   "@
3504    vunpcklps\t{%2, %1, %0|%0, %1, %2}
3505    vinsertps\t{$0x10, %2, %1, %0|%0, %1, %2, 0x10}
3506    vmovss\t{%1, %0|%0, %1}
3507    punpckldq\t{%2, %0|%0, %2}
3508    movd\t{%1, %0|%0, %1}"
3509   [(set_attr "type" "sselog,sselog,ssemov,mmxcvt,mmxmov")
3510    (set (attr "prefix")
3511      (if_then_else (eq_attr "alternative" "3,4")
3512        (const_string "orig")
3513        (const_string "vex")))
3514    (set_attr "mode" "V4SF,V4SF,SF,DI,DI")])
3515
3516 ;; Although insertps takes register source, we prefer
3517 ;; unpcklps with register source since it is shorter.
3518 (define_insn "*vec_concatv2sf_sse4_1"
3519   [(set (match_operand:V2SF 0 "register_operand"     "=x,x,x,*y ,*y")
3520         (vec_concat:V2SF
3521           (match_operand:SF 1 "nonimmediate_operand" " 0,0,m, 0 , m")
3522           (match_operand:SF 2 "vector_move_operand"  " x,m,C,*ym, C")))]
3523   "TARGET_SSE4_1"
3524   "@
3525    unpcklps\t{%2, %0|%0, %2}
3526    insertps\t{$0x10, %2, %0|%0, %2, 0x10}
3527    movss\t{%1, %0|%0, %1}
3528    punpckldq\t{%2, %0|%0, %2}
3529    movd\t{%1, %0|%0, %1}"
3530   [(set_attr "type" "sselog,sselog,ssemov,mmxcvt,mmxmov")
3531    (set_attr "prefix_extra" "*,1,*,*,*")
3532    (set_attr "mode" "V4SF,V4SF,SF,DI,DI")])
3533
3534 ;; ??? In theory we can match memory for the MMX alternative, but allowing
3535 ;; nonimmediate_operand for operand 2 and *not* allowing memory for the SSE
3536 ;; alternatives pretty much forces the MMX alternative to be chosen.
3537 (define_insn "*vec_concatv2sf_sse"
3538   [(set (match_operand:V2SF 0 "register_operand"     "=x,x,*y,*y")
3539         (vec_concat:V2SF
3540           (match_operand:SF 1 "nonimmediate_operand" " 0,m, 0, m")
3541           (match_operand:SF 2 "reg_or_0_operand"     " x,C,*y, C")))]
3542   "TARGET_SSE"
3543   "@
3544    unpcklps\t{%2, %0|%0, %2}
3545    movss\t{%1, %0|%0, %1}
3546    punpckldq\t{%2, %0|%0, %2}
3547    movd\t{%1, %0|%0, %1}"
3548   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
3549    (set_attr "mode" "V4SF,SF,DI,DI")])
3550
3551 (define_insn "*vec_concatv4sf_avx"
3552   [(set (match_operand:V4SF 0 "register_operand"   "=x,x")
3553         (vec_concat:V4SF
3554           (match_operand:V2SF 1 "register_operand" " x,x")
3555           (match_operand:V2SF 2 "nonimmediate_operand" " x,m")))]
3556   "TARGET_AVX"
3557   "@
3558    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3559    vmovhps\t{%2, %1, %0|%0, %1, %2}"
3560   [(set_attr "type" "ssemov")
3561    (set_attr "prefix" "vex")
3562    (set_attr "mode" "V4SF,V2SF")])
3563
3564 (define_insn "*vec_concatv4sf_sse"
3565   [(set (match_operand:V4SF 0 "register_operand"   "=x,x")
3566         (vec_concat:V4SF
3567           (match_operand:V2SF 1 "register_operand" " 0,0")
3568           (match_operand:V2SF 2 "nonimmediate_operand" " x,m")))]
3569   "TARGET_SSE"
3570   "@
3571    movlhps\t{%2, %0|%0, %2}
3572    movhps\t{%2, %0|%0, %2}"
3573   [(set_attr "type" "ssemov")
3574    (set_attr "mode" "V4SF,V2SF")])
3575
3576 (define_expand "vec_init<mode>"
3577   [(match_operand:SSEMODE 0 "register_operand" "")
3578    (match_operand 1 "" "")]
3579   "TARGET_SSE"
3580 {
3581   ix86_expand_vector_init (false, operands[0], operands[1]);
3582   DONE;
3583 })
3584
3585 (define_insn "*vec_setv4sf_0_avx"
3586   [(set (match_operand:V4SF 0 "nonimmediate_operand"  "=x,x,x,m")
3587         (vec_merge:V4SF
3588           (vec_duplicate:V4SF
3589             (match_operand:SF 2 "general_operand"     " x,m,*r,x*rfF"))
3590           (match_operand:V4SF 1 "vector_move_operand" " x,C,C ,0")
3591           (const_int 1)))]
3592   "TARGET_AVX"
3593   "@
3594    vmovss\t{%2, %1, %0|%0, %1, %2}
3595    vmovss\t{%2, %0|%0, %2}
3596    vmovd\t{%2, %0|%0, %2}
3597    #"
3598   [(set_attr "type" "ssemov")
3599    (set_attr "prefix" "vex")
3600    (set_attr "mode" "SF")])
3601
3602 (define_insn "vec_setv4sf_0"
3603   [(set (match_operand:V4SF 0 "nonimmediate_operand"  "=x,x,Y2,m")
3604         (vec_merge:V4SF
3605           (vec_duplicate:V4SF
3606             (match_operand:SF 2 "general_operand"     " x,m,*r,x*rfF"))
3607           (match_operand:V4SF 1 "vector_move_operand" " 0,C,C ,0")
3608           (const_int 1)))]
3609   "TARGET_SSE"
3610   "@
3611    movss\t{%2, %0|%0, %2}
3612    movss\t{%2, %0|%0, %2}
3613    movd\t{%2, %0|%0, %2}
3614    #"
3615   [(set_attr "type" "ssemov")
3616    (set_attr "mode" "SF")])
3617
3618 ;; A subset is vec_setv4sf.
3619 (define_insn "*vec_setv4sf_avx"
3620   [(set (match_operand:V4SF 0 "register_operand" "=x")
3621         (vec_merge:V4SF
3622           (vec_duplicate:V4SF
3623             (match_operand:SF 2 "nonimmediate_operand" "xm"))
3624           (match_operand:V4SF 1 "register_operand" "x")
3625           (match_operand:SI 3 "const_pow2_1_to_8_operand" "n")))]
3626   "TARGET_AVX"
3627 {
3628   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])) << 4);
3629   return "vinsertps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3630 }
3631   [(set_attr "type" "sselog")
3632    (set_attr "prefix" "vex")
3633    (set_attr "mode" "V4SF")])
3634
3635 (define_insn "*vec_setv4sf_sse4_1"
3636   [(set (match_operand:V4SF 0 "register_operand" "=x")
3637         (vec_merge:V4SF
3638           (vec_duplicate:V4SF
3639             (match_operand:SF 2 "nonimmediate_operand" "xm"))
3640           (match_operand:V4SF 1 "register_operand" "0")
3641           (match_operand:SI 3 "const_pow2_1_to_8_operand" "n")))]
3642   "TARGET_SSE4_1"
3643 {
3644   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])) << 4);
3645   return "insertps\t{%3, %2, %0|%0, %2, %3}";
3646 }
3647   [(set_attr "type" "sselog")
3648    (set_attr "prefix_extra" "1")
3649    (set_attr "mode" "V4SF")])
3650
3651 (define_insn "*avx_insertps"
3652   [(set (match_operand:V4SF 0 "register_operand" "=x")
3653         (unspec:V4SF [(match_operand:V4SF 2 "nonimmediate_operand" "xm")
3654                       (match_operand:V4SF 1 "register_operand" "x")
3655                       (match_operand:SI 3 "const_0_to_255_operand" "n")]
3656                      UNSPEC_INSERTPS))]
3657   "TARGET_AVX"
3658   "vinsertps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3659   [(set_attr "type" "sselog")
3660    (set_attr "prefix" "vex")
3661    (set_attr "mode" "V4SF")])
3662
3663 (define_insn "sse4_1_insertps"
3664   [(set (match_operand:V4SF 0 "register_operand" "=x")
3665         (unspec:V4SF [(match_operand:V4SF 2 "register_operand" "x")
3666                       (match_operand:V4SF 1 "register_operand" "0")
3667                       (match_operand:SI 3 "const_0_to_255_operand" "n")]
3668                      UNSPEC_INSERTPS))]
3669   "TARGET_SSE4_1"
3670   "insertps\t{%3, %2, %0|%0, %2, %3}";
3671   [(set_attr "type" "sselog")
3672    (set_attr "prefix_extra" "1")
3673    (set_attr "mode" "V4SF")])
3674
3675 (define_split
3676   [(set (match_operand:V4SF 0 "memory_operand" "")
3677         (vec_merge:V4SF
3678           (vec_duplicate:V4SF
3679             (match_operand:SF 1 "nonmemory_operand" ""))
3680           (match_dup 0)
3681           (const_int 1)))]
3682   "TARGET_SSE && reload_completed"
3683   [(const_int 0)]
3684 {
3685   emit_move_insn (adjust_address (operands[0], SFmode, 0), operands[1]);
3686   DONE;
3687 })
3688
3689 (define_expand "vec_set<mode>"
3690   [(match_operand:SSEMODE 0 "register_operand" "")
3691    (match_operand:<ssescalarmode> 1 "register_operand" "")
3692    (match_operand 2 "const_int_operand" "")]
3693   "TARGET_SSE"
3694 {
3695   ix86_expand_vector_set (false, operands[0], operands[1],
3696                           INTVAL (operands[2]));
3697   DONE;
3698 })
3699
3700 (define_insn_and_split "*vec_extractv4sf_0"
3701   [(set (match_operand:SF 0 "nonimmediate_operand" "=x,m,f,r")
3702         (vec_select:SF
3703           (match_operand:V4SF 1 "nonimmediate_operand" "xm,x,m,m")
3704           (parallel [(const_int 0)])))]
3705   "TARGET_SSE && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3706   "#"
3707   "&& reload_completed"
3708   [(const_int 0)]
3709 {
3710   rtx op1 = operands[1];
3711   if (REG_P (op1))
3712     op1 = gen_rtx_REG (SFmode, REGNO (op1));
3713   else
3714     op1 = gen_lowpart (SFmode, op1);
3715   emit_move_insn (operands[0], op1);
3716   DONE;
3717 })
3718
3719 (define_expand "avx_vextractf128<mode>"
3720   [(match_operand:<avxhalfvecmode> 0 "nonimmediate_operand" "")
3721    (match_operand:AVX256MODE 1 "register_operand" "")
3722    (match_operand:SI 2 "const_0_to_1_operand" "")]
3723   "TARGET_AVX"
3724 {
3725   switch (INTVAL (operands[2]))
3726     {
3727     case 0:
3728       emit_insn (gen_vec_extract_lo_<mode> (operands[0], operands[1]));
3729       break;
3730     case 1:
3731       emit_insn (gen_vec_extract_hi_<mode> (operands[0], operands[1]));
3732       break;
3733     default:
3734       gcc_unreachable ();
3735     }
3736   DONE;
3737 })
3738
3739 (define_insn "vec_extract_lo_<mode>"
3740   [(set (match_operand:<avxhalfvecmode> 0 "nonimmediate_operand" "=x,m")
3741         (vec_select:<avxhalfvecmode>
3742           (match_operand:AVX256MODE4P 1 "register_operand" "x,x")
3743           (parallel [(const_int 0) (const_int 1)])))]
3744   "TARGET_AVX"
3745   "vextractf128\t{$0x0, %1, %0|%0, %1, 0x0}"
3746   [(set_attr "type" "sselog")
3747    (set_attr "memory" "none,store")
3748    (set_attr "prefix" "vex")
3749    (set_attr "mode" "V8SF")])
3750
3751 (define_insn "vec_extract_hi_<mode>"
3752   [(set (match_operand:<avxhalfvecmode> 0 "nonimmediate_operand" "=x,m")
3753         (vec_select:<avxhalfvecmode>
3754           (match_operand:AVX256MODE4P 1 "register_operand" "x,x")
3755           (parallel [(const_int 2) (const_int 3)])))]
3756   "TARGET_AVX"
3757   "vextractf128\t{$0x1, %1, %0|%0, %1, 0x1}"
3758   [(set_attr "type" "sselog")
3759    (set_attr "memory" "none,store")
3760    (set_attr "prefix" "vex")
3761    (set_attr "mode" "V8SF")])
3762
3763 (define_insn "vec_extract_lo_<mode>"
3764   [(set (match_operand:<avxhalfvecmode> 0 "nonimmediate_operand" "=x,m")
3765         (vec_select:<avxhalfvecmode>
3766           (match_operand:AVX256MODE8P 1 "register_operand" "x,x")
3767           (parallel [(const_int 0) (const_int 1)
3768                      (const_int 2) (const_int 3)])))]
3769   "TARGET_AVX"
3770   "vextractf128\t{$0x0, %1, %0|%0, %1, 0x0}"
3771   [(set_attr "type" "sselog")
3772    (set_attr "memory" "none,store")
3773    (set_attr "prefix" "vex")
3774    (set_attr "mode" "V8SF")])
3775
3776 (define_insn "vec_extract_hi_<mode>"
3777   [(set (match_operand:<avxhalfvecmode> 0 "nonimmediate_operand" "=x,m")
3778         (vec_select:<avxhalfvecmode>
3779           (match_operand:AVX256MODE8P 1 "register_operand" "x,x")
3780           (parallel [(const_int 4) (const_int 5)
3781                      (const_int 6) (const_int 7)])))]
3782   "TARGET_AVX"
3783   "vextractf128\t{$0x1, %1, %0|%0, %1, 0x1}"
3784   [(set_attr "type" "sselog")
3785    (set_attr "memory" "none,store")
3786    (set_attr "prefix" "vex")
3787    (set_attr "mode" "V8SF")])
3788
3789 (define_insn "vec_extract_lo_v16hi"
3790   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=x,m")
3791         (vec_select:V8HI
3792           (match_operand:V16HI 1 "register_operand" "x,x")
3793           (parallel [(const_int 0) (const_int 1)
3794                      (const_int 2) (const_int 3)
3795                      (const_int 4) (const_int 5)
3796                      (const_int 6) (const_int 7)])))]
3797   "TARGET_AVX"
3798   "vextractf128\t{$0x0, %1, %0|%0, %1, 0x0}"
3799   [(set_attr "type" "sselog")
3800    (set_attr "memory" "none,store")
3801    (set_attr "prefix" "vex")
3802    (set_attr "mode" "V8SF")])
3803
3804 (define_insn "vec_extract_hi_v16hi"
3805   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=x,m")
3806         (vec_select:V8HI
3807           (match_operand:V16HI 1 "register_operand" "x,x")
3808           (parallel [(const_int 8) (const_int 9)
3809                      (const_int 10) (const_int 11)
3810                      (const_int 12) (const_int 13)
3811                      (const_int 14) (const_int 15)])))]
3812   "TARGET_AVX"
3813   "vextractf128\t{$0x1, %1, %0|%0, %1, 0x1}"
3814   [(set_attr "type" "sselog")
3815    (set_attr "memory" "none,store")
3816    (set_attr "prefix" "vex")
3817    (set_attr "mode" "V8SF")])
3818
3819 (define_insn "vec_extract_lo_v32qi"
3820   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
3821         (vec_select:V16QI
3822           (match_operand:V32QI 1 "register_operand" "x,x")
3823           (parallel [(const_int 0) (const_int 1)
3824                      (const_int 2) (const_int 3)
3825                      (const_int 4) (const_int 5)
3826                      (const_int 6) (const_int 7)
3827                      (const_int 8) (const_int 9)
3828                      (const_int 10) (const_int 11)
3829                      (const_int 12) (const_int 13)
3830                      (const_int 14) (const_int 15)])))]
3831   "TARGET_AVX"
3832   "vextractf128\t{$0x0, %1, %0|%0, %1, 0x0}"
3833   [(set_attr "type" "sselog")
3834    (set_attr "memory" "none,store")
3835    (set_attr "prefix" "vex")
3836    (set_attr "mode" "V8SF")])
3837
3838 (define_insn "vec_extract_hi_v32qi"
3839   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
3840         (vec_select:V16QI
3841           (match_operand:V32QI 1 "register_operand" "x,x")
3842           (parallel [(const_int 16) (const_int 17)
3843                      (const_int 18) (const_int 19)
3844                      (const_int 20) (const_int 21)
3845                      (const_int 22) (const_int 23)
3846                      (const_int 24) (const_int 25)
3847                      (const_int 26) (const_int 27)
3848                      (const_int 28) (const_int 29)
3849                      (const_int 30) (const_int 31)])))]
3850   "TARGET_AVX"
3851   "vextractf128\t{$0x1, %1, %0|%0, %1, 0x1}"
3852   [(set_attr "type" "sselog")
3853    (set_attr "memory" "none,store")
3854    (set_attr "prefix" "vex")
3855    (set_attr "mode" "V8SF")])
3856
3857 (define_insn "*sse4_1_extractps"
3858   [(set (match_operand:SF 0 "nonimmediate_operand" "=rm")
3859         (vec_select:SF
3860           (match_operand:V4SF 1 "register_operand" "x")
3861           (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n")])))]
3862   "TARGET_SSE4_1"
3863   "%vextractps\t{%2, %1, %0|%0, %1, %2}"
3864   [(set_attr "type" "sselog")
3865    (set_attr "prefix_extra" "1")
3866    (set_attr "prefix" "maybe_vex")
3867    (set_attr "mode" "V4SF")])
3868
3869 (define_insn_and_split "*vec_extract_v4sf_mem"
3870   [(set (match_operand:SF 0 "register_operand" "=x*rf")
3871        (vec_select:SF
3872          (match_operand:V4SF 1 "memory_operand" "o")
3873          (parallel [(match_operand 2 "const_0_to_3_operand" "n")])))]
3874   ""
3875   "#"
3876   "reload_completed"
3877   [(const_int 0)]
3878 {
3879   int i = INTVAL (operands[2]);
3880
3881   emit_move_insn (operands[0], adjust_address (operands[1], SFmode, i*4));
3882   DONE;
3883 })
3884
3885 (define_expand "vec_extract<mode>"
3886   [(match_operand:<ssescalarmode> 0 "register_operand" "")
3887    (match_operand:SSEMODE 1 "register_operand" "")
3888    (match_operand 2 "const_int_operand" "")]
3889   "TARGET_SSE"
3890 {
3891   ix86_expand_vector_extract (false, operands[0], operands[1],
3892                               INTVAL (operands[2]));
3893   DONE;
3894 })
3895
3896 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3897 ;;
3898 ;; Parallel double-precision floating point element swizzling
3899 ;;
3900 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3901
3902 (define_insn "avx_unpckhpd256"
3903   [(set (match_operand:V4DF 0 "register_operand" "=x")
3904         (vec_select:V4DF
3905           (vec_concat:V8DF
3906             (match_operand:V4DF 1 "register_operand" "x")
3907             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
3908           (parallel [(const_int 1) (const_int 5)
3909                      (const_int 3) (const_int 7)])))]
3910   "TARGET_AVX"
3911   "vunpckhpd\t{%2, %1, %0|%0, %1, %2}"
3912   [(set_attr "type" "sselog")
3913    (set_attr "prefix" "vex")
3914    (set_attr "mode" "V4DF")])
3915
3916 (define_expand "sse2_unpckhpd_exp"
3917   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
3918         (vec_select:V2DF
3919           (vec_concat:V4DF
3920             (match_operand:V2DF 1 "nonimmediate_operand" "")
3921             (match_operand:V2DF 2 "nonimmediate_operand" ""))
3922           (parallel [(const_int 1)
3923                      (const_int 3)])))]
3924   "TARGET_SSE2"
3925   "ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);")
3926
3927 (define_insn "*avx_unpckhpd"
3928   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,m")
3929         (vec_select:V2DF
3930           (vec_concat:V4DF
3931             (match_operand:V2DF 1 "nonimmediate_operand" " x,o,x")
3932             (match_operand:V2DF 2 "nonimmediate_operand" " x,x,0"))
3933           (parallel [(const_int 1)
3934                      (const_int 3)])))]
3935   "TARGET_AVX && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
3936   "@
3937    vunpckhpd\t{%2, %1, %0|%0, %1, %2}
3938    vmovlpd\t{%H1, %2, %0|%0, %2, %H1}
3939    vmovhpd\t{%1, %0|%0, %1}"
3940   [(set_attr "type" "sselog,ssemov,ssemov")
3941    (set_attr "prefix" "vex")
3942    (set_attr "mode" "V2DF,V1DF,V1DF")])
3943
3944 (define_insn "sse2_unpckhpd"
3945   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,m")
3946         (vec_select:V2DF
3947           (vec_concat:V4DF
3948             (match_operand:V2DF 1 "nonimmediate_operand" " 0,o,x")
3949             (match_operand:V2DF 2 "nonimmediate_operand" " x,0,0"))
3950           (parallel [(const_int 1)
3951                      (const_int 3)])))]
3952   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
3953   "@
3954    unpckhpd\t{%2, %0|%0, %2}
3955    movlpd\t{%H1, %0|%0, %H1}
3956    movhpd\t{%1, %0|%0, %1}"
3957   [(set_attr "type" "sselog,ssemov,ssemov")
3958    (set_attr "mode" "V2DF,V1DF,V1DF")])
3959
3960 (define_insn "avx_movddup256"
3961   [(set (match_operand:V4DF 0 "register_operand" "=x")
3962         (vec_select:V4DF
3963           (vec_concat:V8DF
3964             (match_operand:V4DF 1 "nonimmediate_operand" "xm")
3965             (match_dup 1))
3966           (parallel [(const_int 0) (const_int 2)
3967                      (const_int 4) (const_int 6)])))]
3968   "TARGET_AVX"
3969   "vmovddup\t{%1, %0|%0, %1}"
3970   [(set_attr "type" "sselog1")
3971    (set_attr "prefix" "vex")
3972    (set_attr "mode" "V4DF")])
3973
3974 (define_insn "*avx_movddup"
3975   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,o")
3976         (vec_select:V2DF
3977           (vec_concat:V4DF
3978             (match_operand:V2DF 1 "nonimmediate_operand" "xm,x")
3979             (match_dup 1))
3980           (parallel [(const_int 0)
3981                      (const_int 2)])))]
3982   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3983   "@
3984    vmovddup\t{%1, %0|%0, %1}
3985    #"
3986   [(set_attr "type" "sselog1,ssemov")
3987    (set_attr "prefix" "vex")
3988    (set_attr "mode" "V2DF")])
3989
3990 (define_insn "*sse3_movddup"
3991   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,o")
3992         (vec_select:V2DF
3993           (vec_concat:V4DF
3994             (match_operand:V2DF 1 "nonimmediate_operand" "xm,x")
3995             (match_dup 1))
3996           (parallel [(const_int 0)
3997                      (const_int 2)])))]
3998   "TARGET_SSE3 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3999   "@
4000    movddup\t{%1, %0|%0, %1}
4001    #"
4002   [(set_attr "type" "sselog1,ssemov")
4003    (set_attr "mode" "V2DF")])
4004
4005 (define_split
4006   [(set (match_operand:V2DF 0 "memory_operand" "")
4007         (vec_select:V2DF
4008           (vec_concat:V4DF
4009             (match_operand:V2DF 1 "register_operand" "")
4010             (match_dup 1))
4011           (parallel [(const_int 0)
4012                      (const_int 2)])))]
4013   "TARGET_SSE3 && reload_completed"
4014   [(const_int 0)]
4015 {
4016   rtx low = gen_rtx_REG (DFmode, REGNO (operands[1]));
4017   emit_move_insn (adjust_address (operands[0], DFmode, 0), low);
4018   emit_move_insn (adjust_address (operands[0], DFmode, 8), low);
4019   DONE;
4020 })
4021
4022 (define_insn "avx_unpcklpd256"
4023   [(set (match_operand:V4DF 0 "register_operand" "=x")
4024         (vec_select:V4DF
4025           (vec_concat:V8DF
4026             (match_operand:V4DF 1 "register_operand" "x")
4027             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4028           (parallel [(const_int 0) (const_int 4)
4029                      (const_int 2) (const_int 6)])))]
4030   "TARGET_AVX"
4031   "vunpcklpd\t{%2, %1, %0|%0, %1, %2}"
4032   [(set_attr "type" "sselog")
4033    (set_attr "prefix" "vex")
4034    (set_attr "mode" "V4DF")])
4035
4036 (define_expand "sse2_unpcklpd_exp"
4037   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
4038         (vec_select:V2DF
4039           (vec_concat:V4DF
4040             (match_operand:V2DF 1 "nonimmediate_operand" "")
4041             (match_operand:V2DF 2 "nonimmediate_operand" ""))
4042           (parallel [(const_int 0)
4043                      (const_int 2)])))]
4044   "TARGET_SSE2"
4045   "ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);")
4046
4047 (define_insn "*avx_unpcklpd"
4048   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,o")
4049         (vec_select:V2DF
4050           (vec_concat:V4DF
4051             (match_operand:V2DF 1 "nonimmediate_operand" " x,x,0")
4052             (match_operand:V2DF 2 "nonimmediate_operand" " x,m,x"))
4053           (parallel [(const_int 0)
4054                      (const_int 2)])))]
4055   "TARGET_AVX && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4056   "@
4057    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4058    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4059    vmovlpd\t{%2, %H0|%H0, %2}"
4060   [(set_attr "type" "sselog,ssemov,ssemov")
4061    (set_attr "prefix" "vex")
4062    (set_attr "mode" "V2DF,V1DF,V1DF")])
4063
4064 (define_insn "sse2_unpcklpd"
4065   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,o")
4066         (vec_select:V2DF
4067           (vec_concat:V4DF
4068             (match_operand:V2DF 1 "nonimmediate_operand" " 0,0,0")
4069             (match_operand:V2DF 2 "nonimmediate_operand" " x,m,x"))
4070           (parallel [(const_int 0)
4071                      (const_int 2)])))]
4072   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4073   "@
4074    unpcklpd\t{%2, %0|%0, %2}
4075    movhpd\t{%2, %0|%0, %2}
4076    movlpd\t{%2, %H0|%H0, %2}"
4077   [(set_attr "type" "sselog,ssemov,ssemov")
4078    (set_attr "mode" "V2DF,V1DF,V1DF")])
4079
4080 (define_expand "avx_shufpd256"
4081   [(match_operand:V4DF 0 "register_operand" "")
4082    (match_operand:V4DF 1 "register_operand" "")
4083    (match_operand:V4DF 2 "nonimmediate_operand" "")
4084    (match_operand:SI 3 "const_int_operand" "")]
4085   "TARGET_AVX"
4086 {
4087   int mask = INTVAL (operands[3]);
4088   emit_insn (gen_avx_shufpd256_1 (operands[0], operands[1], operands[2],
4089                                    GEN_INT (mask & 1),
4090                                    GEN_INT (mask & 2 ? 5 : 4),
4091                                    GEN_INT (mask & 4 ? 3 : 2),
4092                                    GEN_INT (mask & 8 ? 7 : 6)));
4093   DONE;
4094 })
4095
4096 (define_insn "avx_shufpd256_1"
4097   [(set (match_operand:V4DF 0 "register_operand" "=x")
4098         (vec_select:V4DF
4099           (vec_concat:V8DF
4100             (match_operand:V4DF 1 "register_operand" "x")
4101             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4102           (parallel [(match_operand 3 "const_0_to_1_operand" "")
4103                      (match_operand 4 "const_4_to_5_operand" "")
4104                      (match_operand 5 "const_2_to_3_operand" "")
4105                      (match_operand 6 "const_6_to_7_operand" "")])))]
4106   "TARGET_AVX"
4107 {
4108   int mask;
4109   mask = INTVAL (operands[3]);
4110   mask |= (INTVAL (operands[4]) - 4) << 1;
4111   mask |= (INTVAL (operands[5]) - 2) << 2;
4112   mask |= (INTVAL (operands[6]) - 6) << 3;
4113   operands[3] = GEN_INT (mask);
4114
4115   return "vshufpd\t{%3, %2, %1, %0|%0, %1, %2, %3}";
4116 }
4117   [(set_attr "type" "sselog")
4118    (set_attr "prefix" "vex")
4119    (set_attr "mode" "V4DF")])
4120
4121 (define_expand "sse2_shufpd"
4122   [(match_operand:V2DF 0 "register_operand" "")
4123    (match_operand:V2DF 1 "register_operand" "")
4124    (match_operand:V2DF 2 "nonimmediate_operand" "")
4125    (match_operand:SI 3 "const_int_operand" "")]
4126   "TARGET_SSE2"
4127 {
4128   int mask = INTVAL (operands[3]);
4129   emit_insn (gen_sse2_shufpd_v2df (operands[0], operands[1], operands[2],
4130                                 GEN_INT (mask & 1),
4131                                 GEN_INT (mask & 2 ? 3 : 2)));
4132   DONE;
4133 })
4134
4135 (define_expand "vec_extract_even<mode>"
4136   [(set (match_operand:SSEMODE4S 0 "register_operand" "")
4137         (vec_select:SSEMODE4S
4138           (vec_concat:<ssedoublesizemode>
4139             (match_operand:SSEMODE4S 1 "register_operand" "")
4140             (match_operand:SSEMODE4S 2 "nonimmediate_operand" ""))
4141           (parallel [(const_int 0)
4142                      (const_int 2)
4143                      (const_int 4)
4144                      (const_int 6)])))]
4145   "TARGET_SSE")
4146
4147 (define_expand "vec_extract_odd<mode>"
4148   [(set (match_operand:SSEMODE4S 0 "register_operand" "")
4149         (vec_select:SSEMODE4S
4150           (vec_concat:<ssedoublesizemode>
4151             (match_operand:SSEMODE4S 1 "register_operand" "")
4152             (match_operand:SSEMODE4S 2 "nonimmediate_operand" ""))
4153           (parallel [(const_int 1)
4154                      (const_int 3)
4155                      (const_int 5)
4156                      (const_int 7)])))]
4157   "TARGET_SSE")
4158
4159 (define_expand "vec_extract_even<mode>"
4160   [(set (match_operand:SSEMODE2D 0 "register_operand" "")
4161         (vec_select:SSEMODE2D
4162           (vec_concat:<ssedoublesizemode>
4163             (match_operand:SSEMODE2D 1 "register_operand" "")
4164             (match_operand:SSEMODE2D 2 "nonimmediate_operand" ""))
4165           (parallel [(const_int 0)
4166                      (const_int 2)])))]
4167   "TARGET_SSE2")
4168
4169 (define_expand "vec_extract_odd<mode>"
4170   [(set (match_operand:SSEMODE2D 0 "register_operand" "")
4171         (vec_select:SSEMODE2D
4172           (vec_concat:<ssedoublesizemode>
4173             (match_operand:SSEMODE2D 1 "register_operand" "")
4174             (match_operand:SSEMODE2D 2 "nonimmediate_operand" ""))
4175           (parallel [(const_int 1)
4176                      (const_int 3)])))]
4177   "TARGET_SSE2")
4178
4179 ;; punpcklqdq and punpckhqdq are shorter than shufpd.
4180 (define_insn "*avx_punpckhqdq"
4181   [(set (match_operand:V2DI 0 "register_operand" "=x")
4182         (vec_select:V2DI
4183           (vec_concat:V4DI
4184             (match_operand:V2DI 1 "register_operand" "x")
4185             (match_operand:V2DI 2 "nonimmediate_operand" "xm"))
4186           (parallel [(const_int 1)
4187                      (const_int 3)])))]
4188   "TARGET_AVX"
4189   "vpunpckhqdq\t{%2, %1, %0|%0, %1, %2}"
4190   [(set_attr "type" "sselog")
4191    (set_attr "prefix" "vex")
4192    (set_attr "mode" "TI")])
4193
4194 (define_insn "sse2_punpckhqdq"
4195   [(set (match_operand:V2DI 0 "register_operand" "=x")
4196         (vec_select:V2DI
4197           (vec_concat:V4DI
4198             (match_operand:V2DI 1 "register_operand" "0")
4199             (match_operand:V2DI 2 "nonimmediate_operand" "xm"))
4200           (parallel [(const_int 1)
4201                      (const_int 3)])))]
4202   "TARGET_SSE2"
4203   "punpckhqdq\t{%2, %0|%0, %2}"
4204   [(set_attr "type" "sselog")
4205    (set_attr "prefix_data16" "1")
4206    (set_attr "mode" "TI")])
4207
4208 (define_insn "*avx_punpcklqdq"
4209   [(set (match_operand:V2DI 0 "register_operand" "=x")
4210         (vec_select:V2DI
4211           (vec_concat:V4DI
4212             (match_operand:V2DI 1 "register_operand" "x")
4213             (match_operand:V2DI 2 "nonimmediate_operand" "xm"))
4214           (parallel [(const_int 0)
4215                      (const_int 2)])))]
4216   "TARGET_AVX"
4217   "vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}"
4218   [(set_attr "type" "sselog")
4219    (set_attr "prefix" "vex")
4220    (set_attr "mode" "TI")])
4221
4222 (define_insn "sse2_punpcklqdq"
4223   [(set (match_operand:V2DI 0 "register_operand" "=x")
4224         (vec_select:V2DI
4225           (vec_concat:V4DI
4226             (match_operand:V2DI 1 "register_operand" "0")
4227             (match_operand:V2DI 2 "nonimmediate_operand" "xm"))
4228           (parallel [(const_int 0)
4229                      (const_int 2)])))]
4230   "TARGET_SSE2"
4231   "punpcklqdq\t{%2, %0|%0, %2}"
4232   [(set_attr "type" "sselog")
4233    (set_attr "prefix_data16" "1")
4234    (set_attr "mode" "TI")])
4235
4236 (define_insn "*avx_shufpd_<mode>"
4237   [(set (match_operand:SSEMODE2D 0 "register_operand" "=x")
4238         (vec_select:SSEMODE2D
4239           (vec_concat:<ssedoublesizemode>
4240             (match_operand:SSEMODE2D 1 "register_operand" "x")
4241             (match_operand:SSEMODE2D 2 "nonimmediate_operand" "xm"))
4242           (parallel [(match_operand 3 "const_0_to_1_operand" "")
4243                      (match_operand 4 "const_2_to_3_operand" "")])))]
4244   "TARGET_AVX"
4245 {
4246   int mask;
4247   mask = INTVAL (operands[3]);
4248   mask |= (INTVAL (operands[4]) - 2) << 1;
4249   operands[3] = GEN_INT (mask);
4250
4251   return "vshufpd\t{%3, %2, %1, %0|%0, %1, %2, %3}";
4252 }
4253   [(set_attr "type" "sselog")
4254    (set_attr "prefix" "vex")
4255    (set_attr "mode" "V2DF")])
4256
4257 (define_insn "sse2_shufpd_<mode>"
4258   [(set (match_operand:SSEMODE2D 0 "register_operand" "=x")
4259         (vec_select:SSEMODE2D
4260           (vec_concat:<ssedoublesizemode>
4261             (match_operand:SSEMODE2D 1 "register_operand" "0")
4262             (match_operand:SSEMODE2D 2 "nonimmediate_operand" "xm"))
4263           (parallel [(match_operand 3 "const_0_to_1_operand" "")
4264                      (match_operand 4 "const_2_to_3_operand" "")])))]
4265   "TARGET_SSE2"
4266 {
4267   int mask;
4268   mask = INTVAL (operands[3]);
4269   mask |= (INTVAL (operands[4]) - 2) << 1;
4270   operands[3] = GEN_INT (mask);
4271
4272   return "shufpd\t{%3, %2, %0|%0, %2, %3}";
4273 }
4274   [(set_attr "type" "sselog")
4275    (set_attr "mode" "V2DF")])
4276
4277 ;; Avoid combining registers from different units in a single alternative,
4278 ;; see comment above inline_secondary_memory_needed function in i386.c
4279 (define_insn "*avx_storehpd"
4280   [(set (match_operand:DF 0 "nonimmediate_operand"     "=m,x,x,*f,r")
4281         (vec_select:DF
4282           (match_operand:V2DF 1 "nonimmediate_operand" " x,x,o,o,o")
4283           (parallel [(const_int 1)])))]
4284   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4285   "@
4286    vmovhpd\t{%1, %0|%0, %1}
4287    vunpckhpd\t{%1, %1, %0|%0, %1, %1}
4288    #
4289    #
4290    #"
4291   [(set_attr "type" "ssemov,sselog1,ssemov,fmov,imov")
4292    (set_attr "prefix" "vex")
4293    (set_attr "mode" "V1DF,V2DF,DF,DF,DF")])
4294
4295 (define_insn "sse2_storehpd"
4296   [(set (match_operand:DF 0 "nonimmediate_operand"     "=m,x,x,*f,r")
4297         (vec_select:DF
4298           (match_operand:V2DF 1 "nonimmediate_operand" " x,0,o,o,o")
4299           (parallel [(const_int 1)])))]
4300   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4301   "@
4302    movhpd\t{%1, %0|%0, %1}
4303    unpckhpd\t%0, %0
4304    #
4305    #
4306    #"
4307   [(set_attr "type" "ssemov,sselog1,ssemov,fmov,imov")
4308    (set_attr "mode" "V1DF,V2DF,DF,DF,DF")])
4309
4310 (define_split
4311   [(set (match_operand:DF 0 "register_operand" "")
4312         (vec_select:DF
4313           (match_operand:V2DF 1 "memory_operand" "")
4314           (parallel [(const_int 1)])))]
4315   "TARGET_SSE2 && reload_completed"
4316   [(set (match_dup 0) (match_dup 1))]
4317 {
4318   operands[1] = adjust_address (operands[1], DFmode, 8);
4319 })
4320
4321 ;; Avoid combining registers from different units in a single alternative,
4322 ;; see comment above inline_secondary_memory_needed function in i386.c
4323 (define_insn "sse2_storelpd"
4324   [(set (match_operand:DF 0 "nonimmediate_operand"     "=m,x,x,*f,r")
4325         (vec_select:DF
4326           (match_operand:V2DF 1 "nonimmediate_operand" " x,x,m,m,m")
4327           (parallel [(const_int 0)])))]
4328   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4329   "@
4330    %vmovlpd\t{%1, %0|%0, %1}
4331    #
4332    #
4333    #
4334    #"
4335   [(set_attr "type" "ssemov,ssemov,ssemov,fmov,imov")
4336    (set_attr "prefix" "maybe_vex")
4337    (set_attr "mode" "V1DF,DF,DF,DF,DF")])
4338
4339 (define_split
4340   [(set (match_operand:DF 0 "register_operand" "")
4341         (vec_select:DF
4342           (match_operand:V2DF 1 "nonimmediate_operand" "")
4343           (parallel [(const_int 0)])))]
4344   "TARGET_SSE2 && reload_completed"
4345   [(const_int 0)]
4346 {
4347   rtx op1 = operands[1];
4348   if (REG_P (op1))
4349     op1 = gen_rtx_REG (DFmode, REGNO (op1));
4350   else
4351     op1 = gen_lowpart (DFmode, op1);
4352   emit_move_insn (operands[0], op1);
4353   DONE;
4354 })
4355
4356 (define_expand "sse2_loadhpd_exp"
4357   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
4358         (vec_concat:V2DF
4359           (vec_select:DF
4360             (match_operand:V2DF 1 "nonimmediate_operand" "")
4361             (parallel [(const_int 0)]))
4362           (match_operand:DF 2 "nonimmediate_operand" "")))]
4363   "TARGET_SSE2"
4364   "ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);")
4365
4366 ;; Avoid combining registers from different units in a single alternative,
4367 ;; see comment above inline_secondary_memory_needed function in i386.c
4368 (define_insn "*avx_loadhpd"
4369   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,o,o,o")
4370         (vec_concat:V2DF
4371           (vec_select:DF
4372             (match_operand:V2DF 1 "nonimmediate_operand" " x,x,0,0,0")
4373             (parallel [(const_int 0)]))
4374           (match_operand:DF 2 "nonimmediate_operand"     " m,x,x,*f,r")))]
4375   "TARGET_AVX && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4376   "@
4377    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4378    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4379    #
4380    #
4381    #"
4382   [(set_attr "type" "ssemov,sselog,ssemov,fmov,imov")
4383    (set_attr "prefix" "vex")
4384    (set_attr "mode" "V1DF,V2DF,DF,DF,DF")])
4385
4386 (define_insn "sse2_loadhpd"
4387   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,x,o,o,o")
4388         (vec_concat:V2DF
4389           (vec_select:DF
4390             (match_operand:V2DF 1 "nonimmediate_operand" " 0,0,x,0,0,0")
4391             (parallel [(const_int 0)]))
4392           (match_operand:DF 2 "nonimmediate_operand"     " m,x,0,x,*f,r")))]
4393   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4394   "@
4395    movhpd\t{%2, %0|%0, %2}
4396    unpcklpd\t{%2, %0|%0, %2}
4397    shufpd\t{$1, %1, %0|%0, %1, 1}
4398    #
4399    #
4400    #"
4401   [(set_attr "type" "ssemov,sselog,sselog,ssemov,fmov,imov")
4402    (set_attr "mode" "V1DF,V2DF,V2DF,DF,DF,DF")])
4403
4404 (define_split
4405   [(set (match_operand:V2DF 0 "memory_operand" "")
4406         (vec_concat:V2DF
4407           (vec_select:DF (match_dup 0) (parallel [(const_int 0)]))
4408           (match_operand:DF 1 "register_operand" "")))]
4409   "TARGET_SSE2 && reload_completed"
4410   [(set (match_dup 0) (match_dup 1))]
4411 {
4412   operands[0] = adjust_address (operands[0], DFmode, 8);
4413 })
4414
4415 (define_expand "sse2_loadlpd_exp"
4416   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
4417         (vec_concat:V2DF
4418           (match_operand:DF 2 "nonimmediate_operand" "")
4419           (vec_select:DF
4420             (match_operand:V2DF 1 "nonimmediate_operand" "")
4421             (parallel [(const_int 1)]))))]
4422   "TARGET_SSE2"
4423   "ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);")
4424
4425 ;; Avoid combining registers from different units in a single alternative,
4426 ;; see comment above inline_secondary_memory_needed function in i386.c
4427 (define_insn "*avx_loadlpd"
4428   [(set (match_operand:V2DF 0 "nonimmediate_operand"    "=x,x,x,x,m,m,m")
4429         (vec_concat:V2DF
4430           (match_operand:DF 2 "nonimmediate_operand"    " m,m,x,x,x,*f,r")
4431           (vec_select:DF
4432             (match_operand:V2DF 1 "vector_move_operand" " C,x,x,o,0,0,0")
4433             (parallel [(const_int 1)]))))]
4434   "TARGET_AVX && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4435   "@
4436    vmovsd\t{%2, %0|%0, %2}
4437    vmovlpd\t{%2, %1, %0|%0, %1, %2}
4438    vmovsd\t{%2, %1, %0|%0, %1, %2}
4439    vmovhpd\t{%H1, %2, %0|%0, %2, %H1}
4440    #
4441    #
4442    #"
4443   [(set_attr "type" "ssemov,ssemov,ssemov,ssemov,ssemov,fmov,imov")
4444    (set_attr "prefix" "vex")
4445    (set_attr "mode" "DF,V1DF,V1DF,V1DF,DF,DF,DF")])
4446
4447 (define_insn "sse2_loadlpd"
4448   [(set (match_operand:V2DF 0 "nonimmediate_operand"    "=x,x,x,x,x,m,m,m")
4449         (vec_concat:V2DF
4450           (match_operand:DF 2 "nonimmediate_operand"    " m,m,x,0,0,x,*f,r")
4451           (vec_select:DF
4452             (match_operand:V2DF 1 "vector_move_operand" " C,0,0,x,o,0,0,0")
4453             (parallel [(const_int 1)]))))]
4454   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4455   "@
4456    movsd\t{%2, %0|%0, %2}
4457    movlpd\t{%2, %0|%0, %2}
4458    movsd\t{%2, %0|%0, %2}
4459    shufpd\t{$2, %1, %0|%0, %1, 2}
4460    movhpd\t{%H1, %0|%0, %H1}
4461    #
4462    #
4463    #"
4464   [(set_attr "type" "ssemov,ssemov,ssemov,sselog,ssemov,ssemov,fmov,imov")
4465    (set_attr "mode" "DF,V1DF,V1DF,V2DF,V1DF,DF,DF,DF")])
4466
4467 (define_split
4468   [(set (match_operand:V2DF 0 "memory_operand" "")
4469         (vec_concat:V2DF
4470           (match_operand:DF 1 "register_operand" "")
4471           (vec_select:DF (match_dup 0) (parallel [(const_int 1)]))))]
4472   "TARGET_SSE2 && reload_completed"
4473   [(set (match_dup 0) (match_dup 1))]
4474 {
4475   operands[0] = adjust_address (operands[0], DFmode, 8);
4476 })
4477
4478 ;; Not sure these two are ever used, but it doesn't hurt to have
4479 ;; them. -aoliva
4480 (define_insn "*vec_extractv2df_1_sse"
4481   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,x,x")
4482         (vec_select:DF
4483           (match_operand:V2DF 1 "nonimmediate_operand" "x,x,o")
4484           (parallel [(const_int 1)])))]
4485   "!TARGET_SSE2 && TARGET_SSE
4486    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4487   "@
4488    movhps\t{%1, %0|%0, %1}
4489    movhlps\t{%1, %0|%0, %1}
4490    movlps\t{%H1, %0|%0, %H1}"
4491   [(set_attr "type" "ssemov")
4492    (set_attr "mode" "V2SF,V4SF,V2SF")])
4493
4494 (define_insn "*vec_extractv2df_0_sse"
4495   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,x,x")
4496         (vec_select:DF
4497           (match_operand:V2DF 1 "nonimmediate_operand" "x,x,m")
4498           (parallel [(const_int 0)])))]
4499   "!TARGET_SSE2 && TARGET_SSE
4500    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4501   "@
4502    movlps\t{%1, %0|%0, %1}
4503    movaps\t{%1, %0|%0, %1}
4504    movlps\t{%1, %0|%0, %1}"
4505   [(set_attr "type" "ssemov")
4506    (set_attr "mode" "V2SF,V4SF,V2SF")])
4507
4508 (define_insn "*avx_movsd"
4509   [(set (match_operand:V2DF 0 "nonimmediate_operand"   "=x,x,m,x,o")
4510         (vec_merge:V2DF
4511           (match_operand:V2DF 2 "nonimmediate_operand" " x,m,x,x,0")
4512           (match_operand:V2DF 1 "nonimmediate_operand" " x,x,0,o,x")
4513           (const_int 1)))]
4514   "TARGET_AVX"
4515   "@
4516    vmovsd\t{%2, %1, %0|%0, %1, %2}
4517    vmovlpd\t{%2, %1, %0|%0, %1, %2}
4518    vmovlpd\t{%2, %0|%0, %2}
4519    vmovhps\t{%H1, %2, %0|%0, %2, %H1}
4520    vmovhps\t{%1, %H0|%H0, %1}"
4521   [(set_attr "type" "ssemov,ssemov,ssemov,ssemov,ssemov")
4522    (set_attr "prefix" "vex")
4523    (set_attr "mode" "DF,V1DF,V1DF,V1DF,V1DF")])
4524
4525 (define_insn "sse2_movsd"
4526   [(set (match_operand:V2DF 0 "nonimmediate_operand"   "=x,x,m,x,x,o")
4527         (vec_merge:V2DF
4528           (match_operand:V2DF 2 "nonimmediate_operand" " x,m,x,0,0,0")
4529           (match_operand:V2DF 1 "nonimmediate_operand" " 0,0,0,x,o,x")
4530           (const_int 1)))]
4531   "TARGET_SSE2"
4532   "@
4533    movsd\t{%2, %0|%0, %2}
4534    movlpd\t{%2, %0|%0, %2}
4535    movlpd\t{%2, %0|%0, %2}
4536    shufpd\t{$2, %1, %0|%0, %1, 2}
4537    movhps\t{%H1, %0|%0, %H1}
4538    movhps\t{%1, %H0|%H0, %1}"
4539   [(set_attr "type" "ssemov,ssemov,ssemov,sselog,ssemov,ssemov")
4540    (set_attr "mode" "DF,V1DF,V1DF,V2DF,V1DF,V1DF")])
4541
4542 (define_insn "*vec_dupv2df_sse3"
4543   [(set (match_operand:V2DF 0 "register_operand" "=x")
4544         (vec_duplicate:V2DF
4545           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4546   "TARGET_SSE3"
4547   "%vmovddup\t{%1, %0|%0, %1}"
4548   [(set_attr "type" "sselog1")
4549    (set_attr "prefix" "maybe_vex")
4550    (set_attr "mode" "DF")])
4551
4552 (define_insn "vec_dupv2df"
4553   [(set (match_operand:V2DF 0 "register_operand" "=x")
4554         (vec_duplicate:V2DF
4555           (match_operand:DF 1 "register_operand" "0")))]
4556   "TARGET_SSE2"
4557   "unpcklpd\t%0, %0"
4558   [(set_attr "type" "sselog1")
4559    (set_attr "mode" "V2DF")])
4560
4561 (define_insn "*vec_concatv2df_sse3"
4562   [(set (match_operand:V2DF 0 "register_operand" "=x")
4563         (vec_concat:V2DF
4564           (match_operand:DF 1 "nonimmediate_operand" "xm")
4565           (match_dup 1)))]
4566   "TARGET_SSE3"
4567   "%vmovddup\t{%1, %0|%0, %1}"
4568   [(set_attr "type" "sselog1")
4569    (set_attr "prefix" "maybe_vex")
4570    (set_attr "mode" "DF")])
4571
4572 (define_insn "*vec_concatv2df_avx"
4573   [(set (match_operand:V2DF 0 "register_operand"     "=x,x,x")
4574         (vec_concat:V2DF
4575           (match_operand:DF 1 "nonimmediate_operand" " x,x,m")
4576           (match_operand:DF 2 "vector_move_operand"  " x,m,C")))]
4577   "TARGET_AVX"
4578   "@
4579    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4580    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4581    vmovsd\t{%1, %0|%0, %1}"
4582   [(set_attr "type" "ssemov")
4583    (set_attr "prefix" "vex")
4584    (set_attr "mode" "DF,V1DF,DF")])
4585
4586 (define_insn "*vec_concatv2df"
4587   [(set (match_operand:V2DF 0 "register_operand"     "=Y2,Y2,Y2,x,x")
4588         (vec_concat:V2DF
4589           (match_operand:DF 1 "nonimmediate_operand" " 0 ,0 ,m ,0,0")
4590           (match_operand:DF 2 "vector_move_operand"  " Y2,m ,C ,x,m")))]
4591   "TARGET_SSE"
4592   "@
4593    unpcklpd\t{%2, %0|%0, %2}
4594    movhpd\t{%2, %0|%0, %2}
4595    movsd\t{%1, %0|%0, %1}
4596    movlhps\t{%2, %0|%0, %2}
4597    movhps\t{%2, %0|%0, %2}"
4598   [(set_attr "type" "sselog,ssemov,ssemov,ssemov,ssemov")
4599    (set_attr "mode" "V2DF,V1DF,DF,V4SF,V2SF")])
4600
4601 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4602 ;;
4603 ;; Parallel integral arithmetic
4604 ;;
4605 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4606
4607 (define_expand "neg<mode>2"
4608   [(set (match_operand:SSEMODEI 0 "register_operand" "")
4609         (minus:SSEMODEI
4610           (match_dup 2)
4611           (match_operand:SSEMODEI 1 "nonimmediate_operand" "")))]
4612   "TARGET_SSE2"
4613   "operands[2] = force_reg (<MODE>mode, CONST0_RTX (<MODE>mode));")
4614
4615 (define_expand "<plusminus_insn><mode>3"
4616   [(set (match_operand:SSEMODEI 0 "register_operand" "")
4617         (plusminus:SSEMODEI
4618           (match_operand:SSEMODEI 1 "nonimmediate_operand" "")
4619           (match_operand:SSEMODEI 2 "nonimmediate_operand" "")))]
4620   "TARGET_SSE2"
4621   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
4622
4623 (define_insn "*avx_<plusminus_insn><mode>3"
4624   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
4625         (plusminus:SSEMODEI
4626           (match_operand:SSEMODEI 1 "nonimmediate_operand" "<comm>x")
4627           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
4628   "TARGET_AVX && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4629   "vp<plusminus_mnemonic><ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
4630   [(set_attr "type" "sseiadd")
4631    (set_attr "prefix" "vex")
4632    (set_attr "mode" "TI")])
4633
4634 (define_insn "*<plusminus_insn><mode>3"
4635   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
4636         (plusminus:SSEMODEI
4637           (match_operand:SSEMODEI 1 "nonimmediate_operand" "<comm>0")
4638           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
4639   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4640   "p<plusminus_mnemonic><ssevecsize>\t{%2, %0|%0, %2}"
4641   [(set_attr "type" "sseiadd")
4642    (set_attr "prefix_data16" "1")
4643    (set_attr "mode" "TI")])
4644
4645 (define_expand "sse2_<plusminus_insn><mode>3"
4646   [(set (match_operand:SSEMODE12 0 "register_operand" "")
4647         (sat_plusminus:SSEMODE12
4648           (match_operand:SSEMODE12 1 "nonimmediate_operand" "")
4649           (match_operand:SSEMODE12 2 "nonimmediate_operand" "")))]
4650   "TARGET_SSE2"
4651   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
4652
4653 (define_insn "*avx_<plusminus_insn><mode>3"
4654   [(set (match_operand:SSEMODE12 0 "register_operand" "=x")
4655         (sat_plusminus:SSEMODE12
4656           (match_operand:SSEMODE12 1 "nonimmediate_operand" "<comm>x")
4657           (match_operand:SSEMODE12 2 "nonimmediate_operand" "xm")))]
4658   "TARGET_AVX && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4659   "vp<plusminus_mnemonic><ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
4660   [(set_attr "type" "sseiadd")
4661    (set_attr "prefix" "vex")
4662    (set_attr "mode" "TI")])
4663
4664 (define_insn "*sse2_<plusminus_insn><mode>3"
4665   [(set (match_operand:SSEMODE12 0 "register_operand" "=x")
4666         (sat_plusminus:SSEMODE12
4667           (match_operand:SSEMODE12 1 "nonimmediate_operand" "<comm>0")
4668           (match_operand:SSEMODE12 2 "nonimmediate_operand" "xm")))]
4669   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4670   "p<plusminus_mnemonic><ssevecsize>\t{%2, %0|%0, %2}"
4671   [(set_attr "type" "sseiadd")
4672    (set_attr "prefix_data16" "1")
4673    (set_attr "mode" "TI")])
4674
4675 (define_insn_and_split "mulv16qi3"
4676   [(set (match_operand:V16QI 0 "register_operand" "")
4677         (mult:V16QI (match_operand:V16QI 1 "register_operand" "")
4678                     (match_operand:V16QI 2 "register_operand" "")))]
4679   "TARGET_SSE2
4680    && !(reload_completed || reload_in_progress)"
4681   "#"
4682   "&& 1"
4683   [(const_int 0)]
4684 {
4685   rtx t[12], op0, op[3];
4686   int i;
4687
4688   if (TARGET_SSE5)
4689     {
4690       /* On SSE5, we can take advantage of the pperm instruction to pack and
4691          unpack the bytes.  Unpack data such that we've got a source byte in
4692          each low byte of each word.  We don't care what goes into the high
4693          byte, so put 0 there.  */
4694       for (i = 0; i < 6; ++i)
4695         t[i] = gen_reg_rtx (V8HImode);
4696
4697       for (i = 0; i < 2; i++)
4698         {
4699           op[0] = t[i];
4700           op[1] = operands[i+1];
4701           ix86_expand_sse5_unpack (op, true, true);             /* high bytes */
4702
4703           op[0] = t[i+2];
4704           ix86_expand_sse5_unpack (op, true, false);            /* low bytes */
4705         }
4706
4707       /* Multiply words.  */
4708       emit_insn (gen_mulv8hi3 (t[4], t[0], t[1]));              /* high bytes */
4709       emit_insn (gen_mulv8hi3 (t[5], t[2], t[3]));              /* low  bytes */
4710
4711       /* Pack the low byte of each word back into a single xmm */
4712       op[0] = operands[0];
4713       op[1] = t[5];
4714       op[2] = t[4];
4715       ix86_expand_sse5_pack (op);
4716       DONE;
4717     }
4718
4719   for (i = 0; i < 12; ++i)
4720     t[i] = gen_reg_rtx (V16QImode);
4721
4722   /* Unpack data such that we've got a source byte in each low byte of
4723      each word.  We don't care what goes into the high byte of each word.
4724      Rather than trying to get zero in there, most convenient is to let
4725      it be a copy of the low byte.  */
4726   emit_insn (gen_sse2_punpckhbw (t[0], operands[1], operands[1]));
4727   emit_insn (gen_sse2_punpckhbw (t[1], operands[2], operands[2]));
4728   emit_insn (gen_sse2_punpcklbw (t[2], operands[1], operands[1]));
4729   emit_insn (gen_sse2_punpcklbw (t[3], operands[2], operands[2]));
4730
4731   /* Multiply words.  The end-of-line annotations here give a picture of what
4732      the output of that instruction looks like.  Dot means don't care; the
4733      letters are the bytes of the result with A being the most significant.  */
4734   emit_insn (gen_mulv8hi3 (gen_lowpart (V8HImode, t[4]), /* .A.B.C.D.E.F.G.H */
4735                            gen_lowpart (V8HImode, t[0]),
4736                            gen_lowpart (V8HImode, t[1])));
4737   emit_insn (gen_mulv8hi3 (gen_lowpart (V8HImode, t[5]), /* .I.J.K.L.M.N.O.P */
4738                            gen_lowpart (V8HImode, t[2]),
4739                            gen_lowpart (V8HImode, t[3])));
4740
4741   /* Extract the relevant bytes and merge them back together.  */
4742   emit_insn (gen_sse2_punpckhbw (t[6], t[5], t[4]));    /* ..AI..BJ..CK..DL */
4743   emit_insn (gen_sse2_punpcklbw (t[7], t[5], t[4]));    /* ..EM..FN..GO..HP */
4744   emit_insn (gen_sse2_punpckhbw (t[8], t[7], t[6]));    /* ....AEIM....BFJN */
4745   emit_insn (gen_sse2_punpcklbw (t[9], t[7], t[6]));    /* ....CGKO....DHLP */
4746   emit_insn (gen_sse2_punpckhbw (t[10], t[9], t[8]));   /* ........ACEGIKMO */
4747   emit_insn (gen_sse2_punpcklbw (t[11], t[9], t[8]));   /* ........BDFHJLNP */
4748
4749   op0 = operands[0];
4750   emit_insn (gen_sse2_punpcklbw (op0, t[11], t[10]));   /* ABCDEFGHIJKLMNOP */
4751   DONE;
4752 })
4753
4754 (define_expand "mulv8hi3"
4755   [(set (match_operand:V8HI 0 "register_operand" "")
4756         (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "")
4757                    (match_operand:V8HI 2 "nonimmediate_operand" "")))]
4758   "TARGET_SSE2"
4759   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
4760
4761 (define_insn "*avx_mulv8hi3"
4762   [(set (match_operand:V8HI 0 "register_operand" "=x")
4763         (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "%x")
4764                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
4765   "TARGET_AVX && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4766   "vpmullw\t{%2, %1, %0|%0, %1, %2}"
4767   [(set_attr "type" "sseimul")
4768    (set_attr "prefix" "vex")
4769    (set_attr "mode" "TI")])
4770
4771 (define_insn "*mulv8hi3"
4772   [(set (match_operand:V8HI 0 "register_operand" "=x")
4773         (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "%0")
4774                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
4775   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4776   "pmullw\t{%2, %0|%0, %2}"
4777   [(set_attr "type" "sseimul")
4778    (set_attr "prefix_data16" "1")
4779    (set_attr "mode" "TI")])
4780
4781 (define_expand "smulv8hi3_highpart"
4782   [(set (match_operand:V8HI 0 "register_operand" "")
4783         (truncate:V8HI
4784           (lshiftrt:V8SI
4785             (mult:V8SI
4786               (sign_extend:V8SI
4787                 (match_operand:V8HI 1 "nonimmediate_operand" ""))
4788               (sign_extend:V8SI
4789                 (match_operand:V8HI 2 "nonimmediate_operand" "")))
4790             (const_int 16))))]
4791   "TARGET_SSE2"
4792   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
4793
4794 (define_insn "*avxv8hi3_highpart"
4795   [(set (match_operand:V8HI 0 "register_operand" "=x")
4796         (truncate:V8HI
4797           (lshiftrt:V8SI
4798             (mult:V8SI
4799               (sign_extend:V8SI
4800                 (match_operand:V8HI 1 "nonimmediate_operand" "%x"))
4801               (sign_extend:V8SI
4802                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
4803             (const_int 16))))]
4804   "TARGET_AVX && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4805   "vpmulhw\t{%2, %1, %0|%0, %1, %2}"
4806   [(set_attr "type" "sseimul")
4807    (set_attr "prefix" "vex")
4808    (set_attr "mode" "TI")])
4809
4810 (define_insn "*smulv8hi3_highpart"
4811   [(set (match_operand:V8HI 0 "register_operand" "=x")
4812         (truncate:V8HI
4813           (lshiftrt:V8SI
4814             (mult:V8SI
4815               (sign_extend:V8SI
4816                 (match_operand:V8HI 1 "nonimmediate_operand" "%0"))
4817               (sign_extend:V8SI
4818                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
4819             (const_int 16))))]
4820   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4821   "pmulhw\t{%2, %0|%0, %2}"
4822   [(set_attr "type" "sseimul")
4823    (set_attr "prefix_data16" "1")
4824    (set_attr "mode" "TI")])
4825
4826 (define_expand "umulv8hi3_highpart"
4827   [(set (match_operand:V8HI 0 "register_operand" "")
4828         (truncate:V8HI
4829           (lshiftrt:V8SI
4830             (mult:V8SI
4831               (zero_extend:V8SI
4832                 (match_operand:V8HI 1 "nonimmediate_operand" ""))
4833               (zero_extend:V8SI
4834                 (match_operand:V8HI 2 "nonimmediate_operand" "")))
4835             (const_int 16))))]
4836   "TARGET_SSE2"
4837   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
4838
4839 (define_insn "*avx_umulv8hi3_highpart"
4840   [(set (match_operand:V8HI 0 "register_operand" "=x")
4841         (truncate:V8HI
4842           (lshiftrt:V8SI
4843             (mult:V8SI
4844               (zero_extend:V8SI
4845                 (match_operand:V8HI 1 "nonimmediate_operand" "%x"))
4846               (zero_extend:V8SI
4847                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
4848             (const_int 16))))]
4849   "TARGET_AVX && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4850   "vpmulhuw\t{%2, %1, %0|%0, %1, %2}"
4851   [(set_attr "type" "sseimul")
4852    (set_attr "prefix" "vex")
4853    (set_attr "mode" "TI")])
4854
4855 (define_insn "*umulv8hi3_highpart"
4856   [(set (match_operand:V8HI 0 "register_operand" "=x")
4857         (truncate:V8HI
4858           (lshiftrt:V8SI
4859             (mult:V8SI
4860               (zero_extend:V8SI
4861                 (match_operand:V8HI 1 "nonimmediate_operand" "%0"))
4862               (zero_extend:V8SI
4863                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
4864             (const_int 16))))]
4865   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
4866   "pmulhuw\t{%2, %0|%0, %2}"
4867   [(set_attr "type" "sseimul")
4868    (set_attr "prefix_data16" "1")
4869    (set_attr "mode" "TI")])
4870
4871 (define_expand "sse2_umulv2siv2di3"
4872   [(set (match_operand:V2DI 0 "register_operand" "")
4873         (mult:V2DI
4874           (zero_extend:V2DI
4875             (vec_select:V2SI
4876               (match_operand:V4SI 1 "nonimmediate_operand" "")
4877               (parallel [(const_int 0) (const_int 2)])))
4878           (zero_extend:V2DI
4879             (vec_select:V2SI
4880               (match_operand:V4SI 2 "nonimmediate_operand" "")
4881               (parallel [(const_int 0) (const_int 2)])))))]
4882   "TARGET_SSE2"
4883   "ix86_fixup_binary_operands_no_copy (MULT, V4SImode, operands);")
4884
4885 (define_insn "*avx_umulv2siv2di3"
4886   [(set (match_operand:V2DI 0 "register_operand" "=x")
4887         (mult:V2DI
4888           (zero_extend:V2DI
4889             (vec_select:V2SI
4890               (match_operand:V4SI 1 "nonimmediate_operand" "%x")
4891               (parallel [(const_int 0) (const_int 2)])))
4892           (zero_extend:V2DI
4893             (vec_select:V2SI
4894               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
4895               (parallel [(const_int 0) (const_int 2)])))))]
4896   "TARGET_AVX && ix86_binary_operator_ok (MULT, V4SImode, operands)"
4897   "vpmuludq\t{%2, %1, %0|%0, %1, %2}"
4898   [(set_attr "type" "sseimul")
4899    (set_attr "prefix" "vex")
4900    (set_attr "mode" "TI")])
4901
4902 (define_insn "*sse2_umulv2siv2di3"
4903   [(set (match_operand:V2DI 0 "register_operand" "=x")
4904         (mult:V2DI
4905           (zero_extend:V2DI
4906             (vec_select:V2SI
4907               (match_operand:V4SI 1 "nonimmediate_operand" "%0")
4908               (parallel [(const_int 0) (const_int 2)])))
4909           (zero_extend:V2DI
4910             (vec_select:V2SI
4911               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
4912               (parallel [(const_int 0) (const_int 2)])))))]
4913   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V4SImode, operands)"
4914   "pmuludq\t{%2, %0|%0, %2}"
4915   [(set_attr "type" "sseimul")
4916    (set_attr "prefix_data16" "1")
4917    (set_attr "mode" "TI")])
4918
4919 (define_expand "sse4_1_mulv2siv2di3"
4920   [(set (match_operand:V2DI 0 "register_operand" "")
4921         (mult:V2DI
4922           (sign_extend:V2DI
4923             (vec_select:V2SI
4924               (match_operand:V4SI 1 "nonimmediate_operand" "")
4925               (parallel [(const_int 0) (const_int 2)])))
4926           (sign_extend:V2DI
4927             (vec_select:V2SI
4928               (match_operand:V4SI 2 "nonimmediate_operand" "")
4929               (parallel [(const_int 0) (const_int 2)])))))]
4930   "TARGET_SSE4_1"
4931   "ix86_fixup_binary_operands_no_copy (MULT, V4SImode, operands);")
4932
4933 (define_insn "*avx_mulv2siv2di3"
4934   [(set (match_operand:V2DI 0 "register_operand" "=x")
4935         (mult:V2DI
4936           (sign_extend:V2DI
4937             (vec_select:V2SI
4938               (match_operand:V4SI 1 "nonimmediate_operand" "%x")
4939               (parallel [(const_int 0) (const_int 2)])))
4940           (sign_extend:V2DI
4941             (vec_select:V2SI
4942               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
4943               (parallel [(const_int 0) (const_int 2)])))))]
4944   "TARGET_AVX && ix86_binary_operator_ok (MULT, V4SImode, operands)"
4945   "vpmuldq\t{%2, %1, %0|%0, %1, %2}"
4946   [(set_attr "type" "sseimul")
4947    (set_attr "prefix" "vex")
4948    (set_attr "mode" "TI")])
4949
4950 (define_insn "*sse4_1_mulv2siv2di3"
4951   [(set (match_operand:V2DI 0 "register_operand" "=x")
4952         (mult:V2DI
4953           (sign_extend:V2DI
4954             (vec_select:V2SI
4955               (match_operand:V4SI 1 "nonimmediate_operand" "%0")
4956               (parallel [(const_int 0) (const_int 2)])))
4957           (sign_extend:V2DI
4958             (vec_select:V2SI
4959               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
4960               (parallel [(const_int 0) (const_int 2)])))))]
4961   "TARGET_SSE4_1 && ix86_binary_operator_ok (MULT, V4SImode, operands)"
4962   "pmuldq\t{%2, %0|%0, %2}"
4963   [(set_attr "type" "sseimul")
4964    (set_attr "prefix_extra" "1")
4965    (set_attr "mode" "TI")])
4966
4967 (define_expand "sse2_pmaddwd"
4968   [(set (match_operand:V4SI 0 "register_operand" "")
4969         (plus:V4SI
4970           (mult:V4SI
4971             (sign_extend:V4SI
4972               (vec_select:V4HI
4973                 (match_operand:V8HI 1 "nonimmediate_operand" "")
4974                 (parallel [(const_int 0)
4975                            (const_int 2)
4976                            (const_int 4)
4977                            (const_int 6)])))
4978             (sign_extend:V4SI
4979               (vec_select:V4HI
4980                 (match_operand:V8HI 2 "nonimmediate_operand" "")
4981                 (parallel [(const_int 0)
4982                            (const_int 2)
4983                            (const_int 4)
4984                            (const_int 6)]))))
4985           (mult:V4SI
4986             (sign_extend:V4SI
4987               (vec_select:V4HI (match_dup 1)
4988                 (parallel [(const_int 1)
4989                            (const_int 3)
4990                            (const_int 5)
4991                            (const_int 7)])))
4992             (sign_extend:V4SI
4993               (vec_select:V4HI (match_dup 2)
4994                 (parallel [(const_int 1)
4995                            (const_int 3)
4996                            (const_int 5)
4997                            (const_int 7)]))))))]
4998   "TARGET_SSE2"
4999   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
5000
5001 (define_insn "*avx_pmaddwd"
5002   [(set (match_operand:V4SI 0 "register_operand" "=x")
5003         (plus:V4SI
5004           (mult:V4SI
5005             (sign_extend:V4SI
5006               (vec_select:V4HI
5007                 (match_operand:V8HI 1 "nonimmediate_operand" "%x")
5008                 (parallel [(const_int 0)
5009                            (const_int 2)
5010                            (const_int 4)
5011                            (const_int 6)])))
5012             (sign_extend:V4SI
5013               (vec_select:V4HI
5014                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")
5015                 (parallel [(const_int 0)
5016                            (const_int 2)
5017                            (const_int 4)
5018                            (const_int 6)]))))
5019           (mult:V4SI
5020             (sign_extend:V4SI
5021               (vec_select:V4HI (match_dup 1)
5022                 (parallel [(const_int 1)
5023                            (const_int 3)
5024                            (const_int 5)
5025                            (const_int 7)])))
5026             (sign_extend:V4SI
5027               (vec_select:V4HI (match_dup 2)
5028                 (parallel [(const_int 1)
5029                            (const_int 3)
5030                            (const_int 5)
5031                            (const_int 7)]))))))]
5032   "TARGET_AVX && ix86_binary_operator_ok (MULT, V8HImode, operands)"
5033   "vpmaddwd\t{%2, %1, %0|%0, %1, %2}"
5034   [(set_attr "type" "sseiadd")
5035    (set_attr "prefix" "vex")
5036    (set_attr "mode" "TI")])
5037
5038 (define_insn "*sse2_pmaddwd"
5039   [(set (match_operand:V4SI 0 "register_operand" "=x")
5040         (plus:V4SI
5041           (mult:V4SI
5042             (sign_extend:V4SI
5043               (vec_select:V4HI
5044                 (match_operand:V8HI 1 "nonimmediate_operand" "%0")
5045                 (parallel [(const_int 0)
5046                            (const_int 2)
5047                            (const_int 4)
5048                            (const_int 6)])))
5049             (sign_extend:V4SI
5050               (vec_select:V4HI
5051                 (match_operand:V8HI 2 "nonimmediate_operand" "xm")
5052                 (parallel [(const_int 0)
5053                            (const_int 2)
5054                            (const_int 4)
5055                            (const_int 6)]))))
5056           (mult:V4SI
5057             (sign_extend:V4SI
5058               (vec_select:V4HI (match_dup 1)
5059                 (parallel [(const_int 1)
5060                            (const_int 3)
5061                            (const_int 5)
5062                            (const_int 7)])))
5063             (sign_extend:V4SI
5064               (vec_select:V4HI (match_dup 2)
5065                 (parallel [(const_int 1)
5066                            (const_int 3)
5067                            (const_int 5)
5068                            (const_int 7)]))))))]
5069   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
5070   "pmaddwd\t{%2, %0|%0, %2}"
5071   [(set_attr "type" "sseiadd")
5072    (set_attr "prefix_data16" "1")
5073    (set_attr "mode" "TI")])
5074
5075 (define_expand "mulv4si3"
5076   [(set (match_operand:V4SI 0 "register_operand" "")
5077         (mult:V4SI (match_operand:V4SI 1 "register_operand" "")
5078                    (match_operand:V4SI 2 "register_operand" "")))]
5079   "TARGET_SSE2"
5080 {
5081   if (TARGET_SSE4_1 || TARGET_SSE5)
5082     ix86_fixup_binary_operands_no_copy (MULT, V4SImode, operands);
5083 })
5084
5085 (define_insn "*avx_mulv4si3"
5086   [(set (match_operand:V4SI 0 "register_operand" "=x")
5087         (mult:V4SI (match_operand:V4SI 1 "nonimmediate_operand" "%x")
5088                    (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
5089   "TARGET_AVX && ix86_binary_operator_ok (MULT, V4SImode, operands)"
5090   "vpmulld\t{%2, %1, %0|%0, %1, %2}"
5091   [(set_attr "type" "sseimul")
5092    (set_attr "prefix" "vex")
5093    (set_attr "mode" "TI")])
5094
5095 (define_insn "*sse4_1_mulv4si3"
5096   [(set (match_operand:V4SI 0 "register_operand" "=x")
5097         (mult:V4SI (match_operand:V4SI 1 "nonimmediate_operand" "%0")
5098                    (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
5099   "TARGET_SSE4_1 && ix86_binary_operator_ok (MULT, V4SImode, operands)"
5100   "pmulld\t{%2, %0|%0, %2}"
5101   [(set_attr "type" "sseimul")
5102    (set_attr "prefix_extra" "1")
5103    (set_attr "mode" "TI")])
5104
5105 ;; We don't have a straight 32-bit parallel multiply on SSE5, so fake it with a
5106 ;; multiply/add.  In general, we expect the define_split to occur before
5107 ;; register allocation, so we have to handle the corner case where the target
5108 ;; is the same as one of the inputs.
5109 (define_insn_and_split "*sse5_mulv4si3"
5110   [(set (match_operand:V4SI 0 "register_operand" "=&x")
5111         (mult:V4SI (match_operand:V4SI 1 "register_operand" "%x")
5112                    (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
5113   "TARGET_SSE5"
5114   "#"
5115   "&& (reload_completed
5116        || (!reg_mentioned_p (operands[0], operands[1])
5117            && !reg_mentioned_p (operands[0], operands[2])))"
5118   [(set (match_dup 0)
5119         (match_dup 3))
5120    (set (match_dup 0)
5121         (plus:V4SI (mult:V4SI (match_dup 1)
5122                               (match_dup 2))
5123                    (match_dup 0)))]
5124 {
5125   operands[3] = CONST0_RTX (V4SImode);
5126 }
5127   [(set_attr "type" "ssemuladd")
5128    (set_attr "mode" "TI")])
5129
5130 (define_insn_and_split "*sse2_mulv4si3"
5131   [(set (match_operand:V4SI 0 "register_operand" "")
5132         (mult:V4SI (match_operand:V4SI 1 "register_operand" "")
5133                    (match_operand:V4SI 2 "register_operand" "")))]
5134   "TARGET_SSE2 && !TARGET_SSE4_1 && !TARGET_SSE5
5135    && !(reload_completed || reload_in_progress)"
5136   "#"
5137   "&& 1"
5138   [(const_int 0)]
5139 {
5140   rtx t1, t2, t3, t4, t5, t6, thirtytwo;
5141   rtx op0, op1, op2;
5142
5143   op0 = operands[0];
5144   op1 = operands[1];
5145   op2 = operands[2];
5146   t1 = gen_reg_rtx (V4SImode);
5147   t2 = gen_reg_rtx (V4SImode);
5148   t3 = gen_reg_rtx (V4SImode);
5149   t4 = gen_reg_rtx (V4SImode);
5150   t5 = gen_reg_rtx (V4SImode);
5151   t6 = gen_reg_rtx (V4SImode);
5152   thirtytwo = GEN_INT (32);
5153
5154   /* Multiply elements 2 and 0.  */
5155   emit_insn (gen_sse2_umulv2siv2di3 (gen_lowpart (V2DImode, t1),
5156                                      op1, op2));
5157
5158   /* Shift both input vectors down one element, so that elements 3
5159      and 1 are now in the slots for elements 2 and 0.  For K8, at
5160      least, this is faster than using a shuffle.  */
5161   emit_insn (gen_sse2_lshrti3 (gen_lowpart (TImode, t2),
5162                                gen_lowpart (TImode, op1),
5163                                thirtytwo));
5164   emit_insn (gen_sse2_lshrti3 (gen_lowpart (TImode, t3),
5165                                gen_lowpart (TImode, op2),
5166                                thirtytwo));
5167   /* Multiply elements 3 and 1.  */
5168   emit_insn (gen_sse2_umulv2siv2di3 (gen_lowpart (V2DImode, t4),
5169                                      t2, t3));
5170
5171   /* Move the results in element 2 down to element 1; we don't care
5172      what goes in elements 2 and 3.  */
5173   emit_insn (gen_sse2_pshufd_1 (t5, t1, const0_rtx, const2_rtx,
5174                                 const0_rtx, const0_rtx));
5175   emit_insn (gen_sse2_pshufd_1 (t6, t4, const0_rtx, const2_rtx,
5176                                 const0_rtx, const0_rtx));
5177
5178   /* Merge the parts back together.  */
5179   emit_insn (gen_sse2_punpckldq (op0, t5, t6));
5180   DONE;
5181 })
5182
5183 (define_insn_and_split "mulv2di3"
5184   [(set (match_operand:V2DI 0 "register_operand" "")
5185         (mult:V2DI (match_operand:V2DI 1 "register_operand" "")
5186                    (match_operand:V2DI 2 "register_operand" "")))]
5187   "TARGET_SSE2
5188    && !(reload_completed || reload_in_progress)"
5189   "#"
5190   "&& 1"
5191   [(const_int 0)]
5192 {
5193   rtx t1, t2, t3, t4, t5, t6, thirtytwo;
5194   rtx op0, op1, op2;
5195
5196   if (TARGET_SSE5)
5197     {
5198       /* op1: A,B,C,D, op2: E,F,G,H */
5199       op0 = operands[0];
5200       op1 = gen_lowpart (V4SImode, operands[1]);
5201       op2 = gen_lowpart (V4SImode, operands[2]);
5202       t1 = gen_reg_rtx (V4SImode);
5203       t2 = gen_reg_rtx (V4SImode);
5204       t3 = gen_reg_rtx (V4SImode);
5205       t4 = gen_reg_rtx (V2DImode);
5206       t5 = gen_reg_rtx (V2DImode);
5207
5208       /* t1: B,A,D,C */
5209       emit_insn (gen_sse2_pshufd_1 (t1, op1,
5210                                     GEN_INT (1),
5211                                     GEN_INT (0),
5212                                     GEN_INT (3),
5213                                     GEN_INT (2)));
5214
5215       /* t2: 0 */
5216       emit_move_insn (t2, CONST0_RTX (V4SImode));
5217
5218       /* t3: (B*E),(A*F),(D*G),(C*H) */
5219       emit_insn (gen_sse5_pmacsdd (t3, t1, op2, t2));
5220
5221       /* t4: (B*E)+(A*F), (D*G)+(C*H) */
5222       emit_insn (gen_sse5_phadddq (t4, t3));
5223
5224       /* t5: ((B*E)+(A*F))<<32, ((D*G)+(C*H))<<32 */
5225       emit_insn (gen_ashlv2di3 (t5, t4, GEN_INT (32)));
5226
5227       /* op0: (((B*E)+(A*F))<<32)+(B*F), (((D*G)+(C*H))<<32)+(D*H) */
5228       emit_insn (gen_sse5_pmacsdql (op0, op1, op2, t5));
5229       DONE;
5230     }
5231
5232   op0 = operands[0];
5233   op1 = operands[1];
5234   op2 = operands[2];
5235   t1 = gen_reg_rtx (V2DImode);
5236   t2 = gen_reg_rtx (V2DImode);
5237   t3 = gen_reg_rtx (V2DImode);
5238   t4 = gen_reg_rtx (V2DImode);
5239   t5 = gen_reg_rtx (V2DImode);
5240   t6 = gen_reg_rtx (V2DImode);
5241   thirtytwo = GEN_INT (32);
5242
5243   /* Multiply low parts.  */
5244   emit_insn (gen_sse2_umulv2siv2di3 (t1, gen_lowpart (V4SImode, op1),
5245                                      gen_lowpart (V4SImode, op2)));
5246
5247   /* Shift input vectors left 32 bits so we can multiply high parts.  */
5248   emit_insn (gen_lshrv2di3 (t2, op1, thirtytwo));
5249   emit_insn (gen_lshrv2di3 (t3, op2, thirtytwo));
5250
5251   /* Multiply high parts by low parts.  */
5252   emit_insn (gen_sse2_umulv2siv2di3 (t4, gen_lowpart (V4SImode, op1),
5253                                      gen_lowpart (V4SImode, t3)));
5254   emit_insn (gen_sse2_umulv2siv2di3 (t5, gen_lowpart (V4SImode, op2),
5255                                      gen_lowpart (V4SImode, t2)));
5256
5257   /* Shift them back.  */
5258   emit_insn (gen_ashlv2di3 (t4, t4, thirtytwo));
5259   emit_insn (gen_ashlv2di3 (t5, t5, thirtytwo));
5260
5261   /* Add the three parts together.  */
5262   emit_insn (gen_addv2di3 (t6, t1, t4));
5263   emit_insn (gen_addv2di3 (op0, t6, t5));
5264   DONE;
5265 })
5266
5267 (define_expand "vec_widen_smult_hi_v8hi"
5268   [(match_operand:V4SI 0 "register_operand" "")
5269    (match_operand:V8HI 1 "register_operand" "")
5270    (match_operand:V8HI 2 "register_operand" "")]
5271   "TARGET_SSE2"
5272 {
5273   rtx op1, op2, t1, t2, dest;
5274
5275   op1 = operands[1];
5276   op2 = operands[2];
5277   t1 = gen_reg_rtx (V8HImode);
5278   t2 = gen_reg_rtx (V8HImode);
5279   dest = gen_lowpart (V8HImode, operands[0]);
5280
5281   emit_insn (gen_mulv8hi3 (t1, op1, op2));
5282   emit_insn (gen_smulv8hi3_highpart (t2, op1, op2));
5283   emit_insn (gen_vec_interleave_highv8hi (dest, t1, t2));
5284   DONE;
5285 })
5286
5287 (define_expand "vec_widen_smult_lo_v8hi"
5288   [(match_operand:V4SI 0 "register_operand" "")
5289    (match_operand:V8HI 1 "register_operand" "")
5290    (match_operand:V8HI 2 "register_operand" "")]
5291   "TARGET_SSE2"
5292 {
5293   rtx op1, op2, t1, t2, dest;
5294
5295   op1 = operands[1];
5296   op2 = operands[2];
5297   t1 = gen_reg_rtx (V8HImode);
5298   t2 = gen_reg_rtx (V8HImode);
5299   dest = gen_lowpart (V8HImode, operands[0]);
5300
5301   emit_insn (gen_mulv8hi3 (t1, op1, op2));
5302   emit_insn (gen_smulv8hi3_highpart (t2, op1, op2));
5303   emit_insn (gen_vec_interleave_lowv8hi (dest, t1, t2));
5304   DONE;
5305 })
5306
5307 (define_expand "vec_widen_umult_hi_v8hi"
5308   [(match_operand:V4SI 0 "register_operand" "")
5309    (match_operand:V8HI 1 "register_operand" "")
5310    (match_operand:V8HI 2 "register_operand" "")]
5311   "TARGET_SSE2"
5312 {
5313   rtx op1, op2, t1, t2, dest;
5314
5315   op1 = operands[1];
5316   op2 = operands[2];
5317   t1 = gen_reg_rtx (V8HImode);
5318   t2 = gen_reg_rtx (V8HImode);
5319   dest = gen_lowpart (V8HImode, operands[0]);
5320
5321   emit_insn (gen_mulv8hi3 (t1, op1, op2));
5322   emit_insn (gen_umulv8hi3_highpart (t2, op1, op2));
5323   emit_insn (gen_vec_interleave_highv8hi (dest, t1, t2));
5324   DONE;
5325 })
5326
5327 (define_expand "vec_widen_umult_lo_v8hi"
5328   [(match_operand:V4SI 0 "register_operand" "")
5329    (match_operand:V8HI 1 "register_operand" "")
5330    (match_operand:V8HI 2 "register_operand" "")]
5331   "TARGET_SSE2"
5332 {
5333   rtx op1, op2, t1, t2, dest;
5334
5335   op1 = operands[1];
5336   op2 = operands[2];
5337   t1 = gen_reg_rtx (V8HImode);
5338   t2 = gen_reg_rtx (V8HImode);
5339   dest = gen_lowpart (V8HImode, operands[0]);
5340
5341   emit_insn (gen_mulv8hi3 (t1, op1, op2));
5342   emit_insn (gen_umulv8hi3_highpart (t2, op1, op2));
5343   emit_insn (gen_vec_interleave_lowv8hi (dest, t1, t2));
5344   DONE;
5345 })
5346
5347 (define_expand "vec_widen_smult_hi_v4si"
5348   [(match_operand:V2DI 0 "register_operand" "")
5349    (match_operand:V4SI 1 "register_operand" "")
5350    (match_operand:V4SI 2 "register_operand" "")]
5351   "TARGET_SSE5"
5352 {
5353   rtx t1, t2;
5354
5355   t1 = gen_reg_rtx (V4SImode);
5356   t2 = gen_reg_rtx (V4SImode);
5357
5358   emit_insn (gen_sse2_pshufd_1 (t1, operands[1],
5359                                 GEN_INT (0),
5360                                 GEN_INT (2),
5361                                 GEN_INT (1),
5362                                 GEN_INT (3)));
5363   emit_insn (gen_sse2_pshufd_1 (t2, operands[2],
5364                                 GEN_INT (0),
5365                                 GEN_INT (2),
5366                                 GEN_INT (1),
5367                                 GEN_INT (3)));
5368   emit_insn (gen_sse5_mulv2div2di3_high (operands[0], t1, t2));
5369   DONE;
5370 })
5371
5372 (define_expand "vec_widen_smult_lo_v4si"
5373   [(match_operand:V2DI 0 "register_operand" "")
5374    (match_operand:V4SI 1 "register_operand" "")
5375    (match_operand:V4SI 2 "register_operand" "")]
5376   "TARGET_SSE5"
5377 {
5378   rtx t1, t2;
5379
5380   t1 = gen_reg_rtx (V4SImode);
5381   t2 = gen_reg_rtx (V4SImode);
5382
5383   emit_insn (gen_sse2_pshufd_1 (t1, operands[1],
5384                                 GEN_INT (0),
5385                                 GEN_INT (2),
5386                                 GEN_INT (1),
5387                                 GEN_INT (3)));
5388   emit_insn (gen_sse2_pshufd_1 (t2, operands[2],
5389                                 GEN_INT (0),
5390                                 GEN_INT (2),
5391                                 GEN_INT (1),
5392                                 GEN_INT (3)));
5393   emit_insn (gen_sse5_mulv2div2di3_low (operands[0], t1, t2));
5394   DONE;
5395   DONE;
5396 })
5397
5398 (define_expand "vec_widen_umult_hi_v4si"
5399   [(match_operand:V2DI 0 "register_operand" "")
5400    (match_operand:V4SI 1 "register_operand" "")
5401    (match_operand:V4SI 2 "register_operand" "")]
5402   "TARGET_SSE2"
5403 {
5404   rtx op1, op2, t1, t2;
5405
5406   op1 = operands[1];
5407   op2 = operands[2];
5408   t1 = gen_reg_rtx (V4SImode);
5409   t2 = gen_reg_rtx (V4SImode);
5410
5411   emit_insn (gen_vec_interleave_highv4si (t1, op1, op1));
5412   emit_insn (gen_vec_interleave_highv4si (t2, op2, op2));
5413   emit_insn (gen_sse2_umulv2siv2di3 (operands[0], t1, t2));
5414   DONE;
5415 })
5416
5417 (define_expand "vec_widen_umult_lo_v4si"
5418   [(match_operand:V2DI 0 "register_operand" "")
5419    (match_operand:V4SI 1 "register_operand" "")
5420    (match_operand:V4SI 2 "register_operand" "")]
5421   "TARGET_SSE2"
5422 {
5423   rtx op1, op2, t1, t2;
5424
5425   op1 = operands[1];
5426   op2 = operands[2];
5427   t1 = gen_reg_rtx (V4SImode);
5428   t2 = gen_reg_rtx (V4SImode);
5429
5430   emit_insn (gen_vec_interleave_lowv4si (t1, op1, op1));
5431   emit_insn (gen_vec_interleave_lowv4si (t2, op2, op2));
5432   emit_insn (gen_sse2_umulv2siv2di3 (operands[0], t1, t2));
5433   DONE;
5434 })
5435
5436 (define_expand "sdot_prodv8hi"
5437   [(match_operand:V4SI 0 "register_operand" "")
5438    (match_operand:V8HI 1 "register_operand" "")
5439    (match_operand:V8HI 2 "register_operand" "")
5440    (match_operand:V4SI 3 "register_operand" "")]
5441   "TARGET_SSE2"
5442 {
5443   rtx t = gen_reg_rtx (V4SImode);
5444   emit_insn (gen_sse2_pmaddwd (t, operands[1], operands[2]));
5445   emit_insn (gen_addv4si3 (operands[0], operands[3], t));
5446   DONE;
5447 })
5448
5449 (define_expand "udot_prodv4si"
5450   [(match_operand:V2DI 0 "register_operand" "")
5451    (match_operand:V4SI 1 "register_operand" "")
5452    (match_operand:V4SI 2 "register_operand" "")
5453    (match_operand:V2DI 3 "register_operand" "")]
5454   "TARGET_SSE2"
5455 {
5456   rtx t1, t2, t3, t4;
5457
5458   t1 = gen_reg_rtx (V2DImode);
5459   emit_insn (gen_sse2_umulv2siv2di3 (t1, operands[1], operands[2]));
5460   emit_insn (gen_addv2di3 (t1, t1, operands[3]));
5461
5462   t2 = gen_reg_rtx (V4SImode);
5463   t3 = gen_reg_rtx (V4SImode);
5464   emit_insn (gen_sse2_lshrti3 (gen_lowpart (TImode, t2),
5465                                gen_lowpart (TImode, operands[1]),
5466                                GEN_INT (32)));
5467   emit_insn (gen_sse2_lshrti3 (gen_lowpart (TImode, t3),
5468                                gen_lowpart (TImode, operands[2]),
5469                                GEN_INT (32)));
5470
5471   t4 = gen_reg_rtx (V2DImode);
5472   emit_insn (gen_sse2_umulv2siv2di3 (t4, t2, t3));
5473
5474   emit_insn (gen_addv2di3 (operands[0], t1, t4));
5475   DONE;
5476 })
5477
5478 (define_insn "*avx_ashr<mode>3"
5479   [(set (match_operand:SSEMODE24 0 "register_operand" "=x")
5480         (ashiftrt:SSEMODE24
5481           (match_operand:SSEMODE24 1 "register_operand" "x")
5482           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5483   "TARGET_AVX"
5484   "vpsra<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5485   [(set_attr "type" "sseishft")
5486    (set_attr "prefix" "vex")
5487    (set_attr "mode" "TI")])
5488
5489 (define_insn "ashr<mode>3"
5490   [(set (match_operand:SSEMODE24 0 "register_operand" "=x")
5491         (ashiftrt:SSEMODE24
5492           (match_operand:SSEMODE24 1 "register_operand" "0")
5493           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5494   "TARGET_SSE2"
5495   "psra<ssevecsize>\t{%2, %0|%0, %2}"
5496   [(set_attr "type" "sseishft")
5497    (set_attr "prefix_data16" "1")
5498    (set_attr "mode" "TI")])
5499
5500 (define_insn "*avx_lshr<mode>3"
5501   [(set (match_operand:SSEMODE248 0 "register_operand" "=x")
5502         (lshiftrt:SSEMODE248
5503           (match_operand:SSEMODE248 1 "register_operand" "x")
5504           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5505   "TARGET_AVX"
5506   "vpsrl<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5507   [(set_attr "type" "sseishft")
5508    (set_attr "prefix" "vex")
5509    (set_attr "mode" "TI")])
5510
5511 (define_insn "lshr<mode>3"
5512   [(set (match_operand:SSEMODE248 0 "register_operand" "=x")
5513         (lshiftrt:SSEMODE248
5514           (match_operand:SSEMODE248 1 "register_operand" "0")
5515           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5516   "TARGET_SSE2"
5517   "psrl<ssevecsize>\t{%2, %0|%0, %2}"
5518   [(set_attr "type" "sseishft")
5519    (set_attr "prefix_data16" "1")
5520    (set_attr "mode" "TI")])
5521
5522 (define_insn "*avx_ashl<mode>3"
5523   [(set (match_operand:SSEMODE248 0 "register_operand" "=x")
5524         (ashift:SSEMODE248
5525           (match_operand:SSEMODE248 1 "register_operand" "x")
5526           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5527   "TARGET_AVX"
5528   "vpsll<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5529   [(set_attr "type" "sseishft")
5530    (set_attr "prefix" "vex")
5531    (set_attr "mode" "TI")])
5532
5533 (define_insn "ashl<mode>3"
5534   [(set (match_operand:SSEMODE248 0 "register_operand" "=x")
5535         (ashift:SSEMODE248
5536           (match_operand:SSEMODE248 1 "register_operand" "0")
5537           (match_operand:SI 2 "nonmemory_operand" "xN")))]
5538   "TARGET_SSE2"
5539   "psll<ssevecsize>\t{%2, %0|%0, %2}"
5540   [(set_attr "type" "sseishft")
5541    (set_attr "prefix_data16" "1")
5542    (set_attr "mode" "TI")])
5543
5544 (define_expand "vec_shl_<mode>"
5545   [(set (match_operand:SSEMODEI 0 "register_operand" "")
5546         (ashift:TI (match_operand:SSEMODEI 1 "register_operand" "")
5547                    (match_operand:SI 2 "const_0_to_255_mul_8_operand" "")))]
5548   "TARGET_SSE2"
5549 {
5550   operands[0] = gen_lowpart (TImode, operands[0]);
5551   operands[1] = gen_lowpart (TImode, operands[1]);
5552 })
5553
5554 (define_expand "vec_shr_<mode>"
5555   [(set (match_operand:SSEMODEI 0 "register_operand" "")
5556         (lshiftrt:TI (match_operand:SSEMODEI 1 "register_operand" "")
5557                      (match_operand:SI 2 "const_0_to_255_mul_8_operand" "")))]
5558   "TARGET_SSE2"
5559 {
5560   operands[0] = gen_lowpart (TImode, operands[0]);
5561   operands[1] = gen_lowpart (TImode, operands[1]);
5562 })
5563
5564 (define_insn "*avx_<code><mode>3"
5565   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
5566         (maxmin:SSEMODE124
5567           (match_operand:SSEMODE124 1 "nonimmediate_operand" "%x")
5568           (match_operand:SSEMODE124 2 "nonimmediate_operand" "xm")))]
5569   "TARGET_AVX && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5570   "vp<maxminiprefix><ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5571   [(set_attr "type" "sseiadd")
5572    (set_attr "prefix" "vex")
5573    (set_attr "mode" "TI")])
5574
5575 (define_expand "<code>v16qi3"
5576   [(set (match_operand:V16QI 0 "register_operand" "")
5577         (umaxmin:V16QI
5578           (match_operand:V16QI 1 "nonimmediate_operand" "")
5579           (match_operand:V16QI 2 "nonimmediate_operand" "")))]
5580   "TARGET_SSE2"
5581   "ix86_fixup_binary_operands_no_copy (<CODE>, V16QImode, operands);")
5582
5583 (define_insn "*<code>v16qi3"
5584   [(set (match_operand:V16QI 0 "register_operand" "=x")
5585         (umaxmin:V16QI
5586           (match_operand:V16QI 1 "nonimmediate_operand" "%0")
5587           (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
5588   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, V16QImode, operands)"
5589   "p<maxminiprefix>b\t{%2, %0|%0, %2}"
5590   [(set_attr "type" "sseiadd")
5591    (set_attr "prefix_data16" "1")
5592    (set_attr "mode" "TI")])
5593
5594 (define_expand "<code>v8hi3"
5595   [(set (match_operand:V8HI 0 "register_operand" "")
5596         (smaxmin:V8HI
5597           (match_operand:V8HI 1 "nonimmediate_operand" "")
5598           (match_operand:V8HI 2 "nonimmediate_operand" "")))]
5599   "TARGET_SSE2"
5600   "ix86_fixup_binary_operands_no_copy (<CODE>, V8HImode, operands);")
5601
5602 (define_insn "*<code>v8hi3"
5603   [(set (match_operand:V8HI 0 "register_operand" "=x")
5604         (smaxmin:V8HI
5605           (match_operand:V8HI 1 "nonimmediate_operand" "%0")
5606           (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
5607   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, V8HImode, operands)"
5608   "p<maxminiprefix>w\t{%2, %0|%0, %2}"
5609   [(set_attr "type" "sseiadd")
5610    (set_attr "prefix_data16" "1")
5611    (set_attr "mode" "TI")])
5612
5613 (define_expand "umaxv8hi3"
5614   [(set (match_operand:V8HI 0 "register_operand" "")
5615         (umax:V8HI (match_operand:V8HI 1 "register_operand" "")
5616                    (match_operand:V8HI 2 "nonimmediate_operand" "")))]
5617   "TARGET_SSE2"
5618 {
5619   if (TARGET_SSE4_1)
5620     ix86_fixup_binary_operands_no_copy (UMAX, V8HImode, operands);
5621   else
5622     {
5623       rtx op0 = operands[0], op2 = operands[2], op3 = op0;
5624       if (rtx_equal_p (op3, op2))
5625         op3 = gen_reg_rtx (V8HImode);
5626       emit_insn (gen_sse2_ussubv8hi3 (op3, operands[1], op2));
5627       emit_insn (gen_addv8hi3 (op0, op3, op2));
5628       DONE;
5629     }
5630 })
5631
5632 (define_expand "smax<mode>3"
5633   [(set (match_operand:SSEMODE14 0 "register_operand" "")
5634         (smax:SSEMODE14 (match_operand:SSEMODE14 1 "register_operand" "")
5635                         (match_operand:SSEMODE14 2 "register_operand" "")))]
5636   "TARGET_SSE2"
5637 {
5638   if (TARGET_SSE4_1)
5639     ix86_fixup_binary_operands_no_copy (SMAX, <MODE>mode, operands);
5640   else
5641   {
5642     rtx xops[6];
5643     bool ok;
5644
5645     xops[0] = operands[0];
5646     xops[1] = operands[1];
5647     xops[2] = operands[2];
5648     xops[3] = gen_rtx_GT (VOIDmode, operands[1], operands[2]);
5649     xops[4] = operands[1];
5650     xops[5] = operands[2];
5651     ok = ix86_expand_int_vcond (xops);
5652     gcc_assert (ok);
5653     DONE;
5654   }
5655 })
5656
5657 (define_insn "*sse4_1_<code><mode>3"
5658   [(set (match_operand:SSEMODE14 0 "register_operand" "=x")
5659         (smaxmin:SSEMODE14
5660           (match_operand:SSEMODE14 1 "nonimmediate_operand" "%0")
5661           (match_operand:SSEMODE14 2 "nonimmediate_operand" "xm")))]
5662   "TARGET_SSE4_1 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5663   "p<maxminiprefix><ssevecsize>\t{%2, %0|%0, %2}"
5664   [(set_attr "type" "sseiadd")
5665    (set_attr "prefix_extra" "1")
5666    (set_attr "mode" "TI")])
5667
5668 (define_expand "umaxv4si3"
5669   [(set (match_operand:V4SI 0 "register_operand" "")
5670         (umax:V4SI (match_operand:V4SI 1 "register_operand" "")
5671                    (match_operand:V4SI 2 "register_operand" "")))]
5672   "TARGET_SSE2"
5673 {
5674   if (TARGET_SSE4_1)
5675     ix86_fixup_binary_operands_no_copy (UMAX, V4SImode, operands);
5676   else
5677   {
5678     rtx xops[6];
5679     bool ok;
5680
5681     xops[0] = operands[0];
5682     xops[1] = operands[1];
5683     xops[2] = operands[2];
5684     xops[3] = gen_rtx_GTU (VOIDmode, operands[1], operands[2]);
5685     xops[4] = operands[1];
5686     xops[5] = operands[2];
5687     ok = ix86_expand_int_vcond (xops);
5688     gcc_assert (ok);
5689     DONE;
5690   }
5691 })
5692
5693 (define_insn "*sse4_1_<code><mode>3"
5694   [(set (match_operand:SSEMODE24 0 "register_operand" "=x")
5695         (umaxmin:SSEMODE24
5696           (match_operand:SSEMODE24 1 "nonimmediate_operand" "%0")
5697           (match_operand:SSEMODE24 2 "nonimmediate_operand" "xm")))]
5698   "TARGET_SSE4_1 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5699   "p<maxminiprefix><ssevecsize>\t{%2, %0|%0, %2}"
5700   [(set_attr "type" "sseiadd")
5701    (set_attr "prefix_extra" "1")
5702    (set_attr "mode" "TI")])
5703
5704 (define_expand "smin<mode>3"
5705   [(set (match_operand:SSEMODE14 0 "register_operand" "")
5706         (smin:SSEMODE14 (match_operand:SSEMODE14 1 "register_operand" "")
5707                         (match_operand:SSEMODE14 2 "register_operand" "")))]
5708   "TARGET_SSE2"
5709 {
5710   if (TARGET_SSE4_1)
5711     ix86_fixup_binary_operands_no_copy (SMIN, <MODE>mode, operands);
5712   else
5713     {
5714       rtx xops[6];
5715       bool ok;
5716
5717       xops[0] = operands[0];
5718       xops[1] = operands[2];
5719       xops[2] = operands[1];
5720       xops[3] = gen_rtx_GT (VOIDmode, operands[1], operands[2]);
5721       xops[4] = operands[1];
5722       xops[5] = operands[2];
5723       ok = ix86_expand_int_vcond (xops);
5724       gcc_assert (ok);
5725       DONE;
5726     }
5727 })
5728
5729 (define_expand "umin<mode>3"
5730   [(set (match_operand:SSEMODE24 0 "register_operand" "")
5731         (umin:SSEMODE24 (match_operand:SSEMODE24 1 "register_operand" "")
5732                         (match_operand:SSEMODE24 2 "register_operand" "")))]
5733   "TARGET_SSE2"
5734 {
5735   if (TARGET_SSE4_1)
5736     ix86_fixup_binary_operands_no_copy (UMIN, <MODE>mode, operands);
5737   else
5738     {
5739       rtx xops[6];
5740       bool ok;
5741
5742       xops[0] = operands[0];
5743       xops[1] = operands[2];
5744       xops[2] = operands[1];
5745       xops[3] = gen_rtx_GTU (VOIDmode, operands[1], operands[2]);
5746       xops[4] = operands[1];
5747       xops[5] = operands[2];
5748       ok = ix86_expand_int_vcond (xops);
5749       gcc_assert (ok);
5750       DONE;
5751     }
5752 })
5753
5754 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
5755 ;;
5756 ;; Parallel integral comparisons
5757 ;;
5758 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
5759
5760 (define_expand "sse2_eq<mode>3"
5761   [(set (match_operand:SSEMODE124 0 "register_operand" "")
5762         (eq:SSEMODE124
5763           (match_operand:SSEMODE124 1 "nonimmediate_operand" "")
5764           (match_operand:SSEMODE124 2 "nonimmediate_operand" "")))]
5765   "TARGET_SSE2 && !TARGET_SSE5"
5766   "ix86_fixup_binary_operands_no_copy (EQ, <MODE>mode, operands);")
5767
5768 (define_insn "*avx_eq<mode>3"
5769   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
5770         (eq:SSEMODE1248
5771           (match_operand:SSEMODE1248 1 "nonimmediate_operand" "%x")
5772           (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm")))]
5773   "TARGET_AVX && ix86_binary_operator_ok (EQ, <MODE>mode, operands)"
5774   "vpcmpeq<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5775   [(set_attr "type" "ssecmp")
5776    (set_attr "prefix" "vex")
5777    (set_attr "mode" "TI")])
5778
5779 (define_insn "*sse2_eq<mode>3"
5780   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
5781         (eq:SSEMODE124
5782           (match_operand:SSEMODE124 1 "nonimmediate_operand" "%0")
5783           (match_operand:SSEMODE124 2 "nonimmediate_operand" "xm")))]
5784   "TARGET_SSE2 && !TARGET_SSE5
5785    && ix86_binary_operator_ok (EQ, <MODE>mode, operands)"
5786   "pcmpeq<ssevecsize>\t{%2, %0|%0, %2}"
5787   [(set_attr "type" "ssecmp")
5788    (set_attr "prefix_data16" "1")
5789    (set_attr "mode" "TI")])
5790
5791 (define_expand "sse4_1_eqv2di3"
5792   [(set (match_operand:V2DI 0 "register_operand" "")
5793         (eq:V2DI
5794           (match_operand:V2DI 1 "nonimmediate_operand" "")
5795           (match_operand:V2DI 2 "nonimmediate_operand" "")))]
5796   "TARGET_SSE4_1"
5797   "ix86_fixup_binary_operands_no_copy (EQ, V2DImode, operands);")
5798
5799 (define_insn "*sse4_1_eqv2di3"
5800   [(set (match_operand:V2DI 0 "register_operand" "=x")
5801         (eq:V2DI
5802           (match_operand:V2DI 1 "nonimmediate_operand" "%0")
5803           (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
5804   "TARGET_SSE4_1 && ix86_binary_operator_ok (EQ, V2DImode, operands)"
5805   "pcmpeqq\t{%2, %0|%0, %2}"
5806   [(set_attr "type" "ssecmp")
5807    (set_attr "prefix_extra" "1")
5808    (set_attr "mode" "TI")])
5809
5810 (define_insn "*avx_gt<mode>3"
5811   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
5812         (gt:SSEMODE1248
5813           (match_operand:SSEMODE1248 1 "register_operand" "x")
5814           (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm")))]
5815   "TARGET_AVX"
5816   "vpcmpgt<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
5817   [(set_attr "type" "ssecmp")
5818    (set_attr "prefix" "vex")
5819    (set_attr "mode" "TI")])
5820
5821 (define_insn "sse2_gt<mode>3"
5822   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
5823         (gt:SSEMODE124
5824           (match_operand:SSEMODE124 1 "register_operand" "0")
5825           (match_operand:SSEMODE124 2 "nonimmediate_operand" "xm")))]
5826   "TARGET_SSE2 && !TARGET_SSE5"
5827   "pcmpgt<ssevecsize>\t{%2, %0|%0, %2}"
5828   [(set_attr "type" "ssecmp")
5829    (set_attr "prefix_data16" "1")
5830    (set_attr "mode" "TI")])
5831
5832 (define_insn "sse4_2_gtv2di3"
5833   [(set (match_operand:V2DI 0 "register_operand" "=x")
5834         (gt:V2DI
5835           (match_operand:V2DI 1 "register_operand" "0")
5836           (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
5837   "TARGET_SSE4_2"
5838   "pcmpgtq\t{%2, %0|%0, %2}"
5839   [(set_attr "type" "ssecmp")
5840    (set_attr "mode" "TI")])
5841
5842 (define_expand "vcond<mode>"
5843   [(set (match_operand:SSEMODE124C8 0 "register_operand" "")
5844         (if_then_else:SSEMODE124C8
5845           (match_operator 3 ""
5846             [(match_operand:SSEMODE124C8 4 "nonimmediate_operand" "")
5847              (match_operand:SSEMODE124C8 5 "nonimmediate_operand" "")])
5848           (match_operand:SSEMODE124C8 1 "general_operand" "")
5849           (match_operand:SSEMODE124C8 2 "general_operand" "")))]
5850   "TARGET_SSE2"
5851 {
5852   bool ok = ix86_expand_int_vcond (operands);
5853   gcc_assert (ok);
5854   DONE;
5855 })
5856
5857 (define_expand "vcondu<mode>"
5858   [(set (match_operand:SSEMODE124C8 0 "register_operand" "")
5859         (if_then_else:SSEMODE124C8
5860           (match_operator 3 ""
5861             [(match_operand:SSEMODE124C8 4 "nonimmediate_operand" "")
5862              (match_operand:SSEMODE124C8 5 "nonimmediate_operand" "")])
5863           (match_operand:SSEMODE124C8 1 "general_operand" "")
5864           (match_operand:SSEMODE124C8 2 "general_operand" "")))]
5865   "TARGET_SSE2"
5866 {
5867   bool ok = ix86_expand_int_vcond (operands);
5868   gcc_assert (ok);
5869   DONE;
5870 })
5871
5872 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
5873 ;;
5874 ;; Parallel bitwise logical operations
5875 ;;
5876 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
5877
5878 (define_expand "one_cmpl<mode>2"
5879   [(set (match_operand:SSEMODEI 0 "register_operand" "")
5880         (xor:SSEMODEI (match_operand:SSEMODEI 1 "nonimmediate_operand" "")
5881                       (match_dup 2)))]
5882   "TARGET_SSE2"
5883 {
5884   int i, n = GET_MODE_NUNITS (<MODE>mode);
5885   rtvec v = rtvec_alloc (n);
5886
5887   for (i = 0; i < n; ++i)
5888     RTVEC_ELT (v, i) = constm1_rtx;
5889
5890   operands[2] = force_reg (<MODE>mode, gen_rtx_CONST_VECTOR (<MODE>mode, v));
5891 })
5892
5893 (define_insn "*avx_andnot<mode>3"
5894   [(set (match_operand:AVX256MODEI 0 "register_operand" "=x")
5895         (and:AVX256MODEI
5896           (not:AVX256MODEI (match_operand:AVX256MODEI 1 "register_operand" "x"))
5897           (match_operand:AVX256MODEI 2 "nonimmediate_operand" "xm")))]
5898   "TARGET_AVX"
5899   "vandnps\t{%2, %1, %0|%0, %1, %2}"
5900   [(set_attr "type" "sselog")
5901    (set_attr "prefix" "vex")
5902    (set_attr "mode" "<avxvecpsmode>")])
5903
5904 (define_insn "*sse_andnot<mode>3"
5905   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5906         (and:SSEMODEI
5907           (not:SSEMODEI (match_operand:SSEMODEI 1 "register_operand" "0"))
5908           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5909   "(TARGET_SSE && !TARGET_SSE2)"
5910   "andnps\t{%2, %0|%0, %2}"
5911   [(set_attr "type" "sselog")
5912    (set_attr "mode" "V4SF")])
5913
5914 (define_insn "*avx_andnot<mode>3"
5915   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5916         (and:SSEMODEI
5917           (not:SSEMODEI (match_operand:SSEMODEI 1 "register_operand" "x"))
5918           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5919   "TARGET_AVX"
5920   "vpandn\t{%2, %1, %0|%0, %1, %2}"
5921   [(set_attr "type" "sselog")
5922    (set_attr "prefix" "vex")
5923    (set_attr "mode" "TI")])
5924
5925 (define_insn "sse2_andnot<mode>3"
5926   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5927         (and:SSEMODEI
5928           (not:SSEMODEI (match_operand:SSEMODEI 1 "register_operand" "0"))
5929           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5930   "TARGET_SSE2"
5931   "pandn\t{%2, %0|%0, %2}"
5932   [(set_attr "type" "sselog")
5933    (set_attr "prefix_data16" "1")
5934    (set_attr "mode" "TI")])
5935
5936 (define_insn "*andnottf3"
5937   [(set (match_operand:TF 0 "register_operand" "=x")
5938         (and:TF
5939           (not:TF (match_operand:TF 1 "register_operand" "0"))
5940           (match_operand:TF 2 "nonimmediate_operand" "xm")))]
5941   "TARGET_SSE2"
5942   "pandn\t{%2, %0|%0, %2}"
5943   [(set_attr "type" "sselog")
5944    (set_attr "prefix_data16" "1")
5945    (set_attr "mode" "TI")])
5946
5947 (define_expand "<code><mode>3"
5948   [(set (match_operand:SSEMODEI 0 "register_operand" "")
5949         (plogic:SSEMODEI
5950           (match_operand:SSEMODEI 1 "nonimmediate_operand" "")
5951           (match_operand:SSEMODEI 2 "nonimmediate_operand" "")))]
5952   "TARGET_SSE"
5953   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
5954
5955 (define_insn "*avx_<code><mode>3"
5956   [(set (match_operand:AVX256MODEI 0 "register_operand" "=x")
5957         (plogic:AVX256MODEI
5958           (match_operand:AVX256MODEI 1 "nonimmediate_operand" "%x")
5959           (match_operand:AVX256MODEI 2 "nonimmediate_operand" "xm")))]
5960   "TARGET_AVX
5961    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5962   "v<plogicprefix>ps\t{%2, %1, %0|%0, %1, %2}"
5963   [(set_attr "type" "sselog")
5964    (set_attr "prefix" "vex")
5965    (set_attr "mode" "<avxvecpsmode>")])
5966
5967 (define_insn "*sse_<code><mode>3"
5968   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5969         (plogic:SSEMODEI
5970           (match_operand:SSEMODEI 1 "nonimmediate_operand" "%0")
5971           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5972   "(TARGET_SSE && !TARGET_SSE2)
5973    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5974   "<plogicprefix>ps\t{%2, %0|%0, %2}"
5975   [(set_attr "type" "sselog")
5976    (set_attr "mode" "V4SF")])
5977
5978 (define_insn "*avx_<code><mode>3"
5979   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5980         (plogic:SSEMODEI
5981           (match_operand:SSEMODEI 1 "nonimmediate_operand" "%x")
5982           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5983   "TARGET_AVX
5984    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5985   "vp<plogicprefix>\t{%2, %1, %0|%0, %1, %2}"
5986   [(set_attr "type" "sselog")
5987    (set_attr "prefix" "vex")
5988    (set_attr "mode" "TI")])
5989
5990 (define_insn "*sse2_<code><mode>3"
5991   [(set (match_operand:SSEMODEI 0 "register_operand" "=x")
5992         (plogic:SSEMODEI
5993           (match_operand:SSEMODEI 1 "nonimmediate_operand" "%0")
5994           (match_operand:SSEMODEI 2 "nonimmediate_operand" "xm")))]
5995   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5996   "p<plogicprefix>\t{%2, %0|%0, %2}"
5997   [(set_attr "type" "sselog")
5998    (set_attr "prefix_data16" "1")
5999    (set_attr "mode" "TI")])
6000
6001 (define_expand "<code>tf3"
6002   [(set (match_operand:TF 0 "register_operand" "")
6003         (plogic:TF
6004           (match_operand:TF 1 "nonimmediate_operand" "")
6005           (match_operand:TF 2 "nonimmediate_operand" "")))]
6006   "TARGET_SSE2"
6007   "ix86_fixup_binary_operands_no_copy (<CODE>, TFmode, operands);")
6008
6009 (define_insn "*<code>tf3"
6010   [(set (match_operand:TF 0 "register_operand" "=x")
6011         (plogic:TF
6012           (match_operand:TF 1 "nonimmediate_operand" "%0")
6013           (match_operand:TF 2 "nonimmediate_operand" "xm")))]
6014   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, TFmode, operands)"
6015   "p<plogicprefix>\t{%2, %0|%0, %2}"
6016   [(set_attr "type" "sselog")
6017    (set_attr "prefix_data16" "1")
6018    (set_attr "mode" "TI")])
6019
6020 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6021 ;;
6022 ;; Parallel integral element swizzling
6023 ;;
6024 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6025
6026 ;; Reduce:
6027 ;;      op1 = abcdefghijklmnop
6028 ;;      op2 = qrstuvwxyz012345
6029 ;;       h1 = aqbrcsdteufvgwhx
6030 ;;       l1 = iyjzk0l1m2n3o4p5
6031 ;;       h2 = aiqybjrzcks0dlt1
6032 ;;       l2 = emu2fnv3gow4hpx5
6033 ;;       h3 = aeimquy2bfjnrvz3
6034 ;;       l3 = cgkosw04dhlptx15
6035 ;;   result = bdfhjlnprtvxz135
6036 (define_expand "vec_pack_trunc_v8hi"
6037   [(match_operand:V16QI 0 "register_operand" "")
6038    (match_operand:V8HI 1 "register_operand" "")
6039    (match_operand:V8HI 2 "register_operand" "")]
6040   "TARGET_SSE2"
6041 {
6042   rtx op1, op2, h1, l1, h2, l2, h3, l3;
6043
6044   if (TARGET_SSE5)
6045     {
6046       ix86_expand_sse5_pack (operands);
6047       DONE;     
6048     }   
6049  
6050   op1 = gen_lowpart (V16QImode, operands[1]);
6051   op2 = gen_lowpart (V16QImode, operands[2]);
6052   h1 = gen_reg_rtx (V16QImode);
6053   l1 = gen_reg_rtx (V16QImode);
6054   h2 = gen_reg_rtx (V16QImode);
6055   l2 = gen_reg_rtx (V16QImode);
6056   h3 = gen_reg_rtx (V16QImode);
6057   l3 = gen_reg_rtx (V16QImode);
6058
6059   emit_insn (gen_vec_interleave_highv16qi (h1, op1, op2));
6060   emit_insn (gen_vec_interleave_lowv16qi (l1, op1, op2));
6061   emit_insn (gen_vec_interleave_highv16qi (h2, l1, h1));
6062   emit_insn (gen_vec_interleave_lowv16qi (l2, l1, h1));
6063   emit_insn (gen_vec_interleave_highv16qi (h3, l2, h2));
6064   emit_insn (gen_vec_interleave_lowv16qi (l3, l2, h2));
6065   emit_insn (gen_vec_interleave_lowv16qi (operands[0], l3, h3));
6066   DONE;
6067 })
6068
6069 ;; Reduce:
6070 ;;      op1 = abcdefgh
6071 ;;      op2 = ijklmnop
6072 ;;       h1 = aibjckdl
6073 ;;       l1 = emfngohp
6074 ;;       h2 = aeimbfjn
6075 ;;       l2 = cgkodhlp
6076 ;;   result = bdfhjlnp
6077 (define_expand "vec_pack_trunc_v4si"
6078   [(match_operand:V8HI 0 "register_operand" "")
6079    (match_operand:V4SI 1 "register_operand" "")
6080    (match_operand:V4SI 2 "register_operand" "")]
6081   "TARGET_SSE2"
6082 {
6083   rtx op1, op2, h1, l1, h2, l2;
6084
6085   if (TARGET_SSE5)
6086     {
6087       ix86_expand_sse5_pack (operands);
6088       DONE;     
6089     }   
6090  
6091   op1 = gen_lowpart (V8HImode, operands[1]);
6092   op2 = gen_lowpart (V8HImode, operands[2]);
6093   h1 = gen_reg_rtx (V8HImode);
6094   l1 = gen_reg_rtx (V8HImode);
6095   h2 = gen_reg_rtx (V8HImode);
6096   l2 = gen_reg_rtx (V8HImode);
6097
6098   emit_insn (gen_vec_interleave_highv8hi (h1, op1, op2));
6099   emit_insn (gen_vec_interleave_lowv8hi (l1, op1, op2));
6100   emit_insn (gen_vec_interleave_highv8hi (h2, l1, h1));
6101   emit_insn (gen_vec_interleave_lowv8hi (l2, l1, h1));
6102   emit_insn (gen_vec_interleave_lowv8hi (operands[0], l2, h2));
6103   DONE;
6104 })
6105
6106 ;; Reduce:
6107 ;;     op1 = abcd
6108 ;;     op2 = efgh
6109 ;;      h1 = aebf
6110 ;;      l1 = cgdh
6111 ;;  result = bdfh
6112 (define_expand "vec_pack_trunc_v2di"
6113   [(match_operand:V4SI 0 "register_operand" "")
6114    (match_operand:V2DI 1 "register_operand" "")
6115    (match_operand:V2DI 2 "register_operand" "")]
6116   "TARGET_SSE2"
6117 {
6118   rtx op1, op2, h1, l1;
6119
6120   if (TARGET_SSE5)
6121     {
6122       ix86_expand_sse5_pack (operands);
6123       DONE;     
6124     }   
6125  
6126   op1 = gen_lowpart (V4SImode, operands[1]);
6127   op2 = gen_lowpart (V4SImode, operands[2]);
6128   h1 = gen_reg_rtx (V4SImode);
6129   l1 = gen_reg_rtx (V4SImode);
6130
6131   emit_insn (gen_vec_interleave_highv4si (h1, op1, op2));
6132   emit_insn (gen_vec_interleave_lowv4si (l1, op1, op2));
6133   emit_insn (gen_vec_interleave_lowv4si (operands[0], l1, h1));
6134   DONE;
6135 })
6136
6137 (define_expand "vec_interleave_highv16qi"
6138   [(set (match_operand:V16QI 0 "register_operand" "")
6139         (vec_select:V16QI
6140           (vec_concat:V32QI
6141             (match_operand:V16QI 1 "register_operand" "")
6142             (match_operand:V16QI 2 "nonimmediate_operand" ""))
6143           (parallel [(const_int 8)  (const_int 24)
6144                      (const_int 9)  (const_int 25)
6145                      (const_int 10) (const_int 26)
6146                      (const_int 11) (const_int 27)
6147                      (const_int 12) (const_int 28)
6148                      (const_int 13) (const_int 29)
6149                      (const_int 14) (const_int 30)
6150                      (const_int 15) (const_int 31)])))]
6151   "TARGET_SSE2"
6152 {
6153   emit_insn (gen_sse2_punpckhbw (operands[0], operands[1], operands[2]));
6154   DONE;
6155 })
6156
6157 (define_expand "vec_interleave_lowv16qi"
6158   [(set (match_operand:V16QI 0 "register_operand" "")
6159         (vec_select:V16QI
6160           (vec_concat:V32QI
6161             (match_operand:V16QI 1 "register_operand" "")
6162             (match_operand:V16QI 2 "nonimmediate_operand" ""))
6163           (parallel [(const_int 0) (const_int 16)
6164                      (const_int 1) (const_int 17)
6165                      (const_int 2) (const_int 18)
6166                      (const_int 3) (const_int 19)
6167                      (const_int 4) (const_int 20)
6168                      (const_int 5) (const_int 21)
6169                      (const_int 6) (const_int 22)
6170                      (const_int 7) (const_int 23)])))]
6171   "TARGET_SSE2"
6172 {
6173   emit_insn (gen_sse2_punpcklbw (operands[0], operands[1], operands[2]));
6174   DONE;
6175 })
6176
6177 (define_expand "vec_interleave_highv8hi"
6178   [(set (match_operand:V8HI 0 "register_operand" "=")
6179         (vec_select:V8HI
6180           (vec_concat:V16HI
6181             (match_operand:V8HI 1 "register_operand" "")
6182             (match_operand:V8HI 2 "nonimmediate_operand" ""))
6183           (parallel [(const_int 4) (const_int 12)
6184                      (const_int 5) (const_int 13)
6185                      (const_int 6) (const_int 14)
6186                      (const_int 7) (const_int 15)])))]
6187   "TARGET_SSE2"
6188 {
6189   emit_insn (gen_sse2_punpckhwd (operands[0], operands[1], operands[2]));
6190   DONE;
6191 })
6192
6193 (define_expand "vec_interleave_lowv8hi"
6194   [(set (match_operand:V8HI 0 "register_operand" "")
6195         (vec_select:V8HI
6196           (vec_concat:V16HI
6197             (match_operand:V8HI 1 "register_operand" "")
6198             (match_operand:V8HI 2 "nonimmediate_operand" ""))
6199           (parallel [(const_int 0) (const_int 8)
6200                      (const_int 1) (const_int 9)
6201                      (const_int 2) (const_int 10)
6202                      (const_int 3) (const_int 11)])))]
6203   "TARGET_SSE2"
6204 {
6205   emit_insn (gen_sse2_punpcklwd (operands[0], operands[1], operands[2]));
6206   DONE;
6207 })
6208
6209 (define_expand "vec_interleave_highv4si"
6210   [(set (match_operand:V4SI 0 "register_operand" "")
6211         (vec_select:V4SI
6212           (vec_concat:V8SI
6213             (match_operand:V4SI 1 "register_operand" "")
6214             (match_operand:V4SI 2 "nonimmediate_operand" ""))
6215           (parallel [(const_int 2) (const_int 6)
6216                      (const_int 3) (const_int 7)])))]
6217   "TARGET_SSE2"
6218 {
6219   emit_insn (gen_sse2_punpckhdq (operands[0], operands[1], operands[2]));
6220   DONE;
6221 })
6222
6223 (define_expand "vec_interleave_lowv4si"
6224   [(set (match_operand:V4SI 0 "register_operand" "")
6225         (vec_select:V4SI
6226           (vec_concat:V8SI
6227             (match_operand:V4SI 1 "register_operand" "")
6228             (match_operand:V4SI 2 "nonimmediate_operand" ""))
6229           (parallel [(const_int 0) (const_int 4)
6230                      (const_int 1) (const_int 5)])))]
6231   "TARGET_SSE2"
6232 {
6233   emit_insn (gen_sse2_punpckldq (operands[0], operands[1], operands[2]));
6234   DONE;
6235 })
6236
6237 (define_expand "vec_interleave_highv2di"
6238   [(set (match_operand:V2DI 0 "register_operand" "")
6239         (vec_select:V2DI
6240           (vec_concat:V4DI
6241             (match_operand:V2DI 1 "register_operand" "")
6242             (match_operand:V2DI 2 "nonimmediate_operand" ""))
6243           (parallel [(const_int 1)
6244                      (const_int 3)])))]
6245   "TARGET_SSE2"
6246 {
6247   emit_insn (gen_sse2_punpckhqdq (operands[0], operands[1], operands[2]));
6248   DONE;
6249 })
6250
6251 (define_expand "vec_interleave_lowv2di"
6252   [(set (match_operand:V2DI 0 "register_operand" "")
6253         (vec_select:V2DI
6254           (vec_concat:V4DI
6255             (match_operand:V2DI 1 "register_operand" "")
6256             (match_operand:V2DI 2 "nonimmediate_operand" ""))
6257           (parallel [(const_int 0)
6258                      (const_int 2)])))]
6259   "TARGET_SSE2"
6260 {
6261   emit_insn (gen_sse2_punpcklqdq (operands[0], operands[1], operands[2]));
6262   DONE;
6263 })
6264
6265 (define_expand "vec_interleave_highv4sf"
6266   [(set (match_operand:V4SF 0 "register_operand" "")
6267         (vec_select:V4SF
6268           (vec_concat:V8SF
6269             (match_operand:V4SF 1 "register_operand" "")
6270             (match_operand:V4SF 2 "nonimmediate_operand" ""))
6271           (parallel [(const_int 2) (const_int 6)
6272                      (const_int 3) (const_int 7)])))]
6273   "TARGET_SSE")
6274
6275 (define_expand "vec_interleave_lowv4sf"
6276   [(set (match_operand:V4SF 0 "register_operand" "")
6277         (vec_select:V4SF
6278           (vec_concat:V8SF
6279             (match_operand:V4SF 1 "register_operand" "")
6280             (match_operand:V4SF 2 "nonimmediate_operand" ""))
6281           (parallel [(const_int 0) (const_int 4)
6282                      (const_int 1) (const_int 5)])))]
6283   "TARGET_SSE")
6284
6285 (define_expand "vec_interleave_highv2df"
6286   [(set (match_operand:V2DF 0 "register_operand" "")
6287         (vec_select:V2DF
6288           (vec_concat:V4DF
6289             (match_operand:V2DF 1 "register_operand" "")
6290             (match_operand:V2DF 2 "nonimmediate_operand" ""))
6291           (parallel [(const_int 1)
6292                      (const_int 3)])))]
6293   "TARGET_SSE2")
6294
6295 (define_expand "vec_interleave_lowv2df"
6296   [(set (match_operand:V2DF 0 "register_operand" "")
6297         (vec_select:V2DF
6298           (vec_concat:V4DF
6299             (match_operand:V2DF 1 "register_operand" "")
6300             (match_operand:V2DF 2 "nonimmediate_operand" ""))
6301           (parallel [(const_int 0)
6302                      (const_int 2)])))]
6303   "TARGET_SSE2")
6304
6305 (define_insn "*avx_packsswb"
6306   [(set (match_operand:V16QI 0 "register_operand" "=x")
6307         (vec_concat:V16QI
6308           (ss_truncate:V8QI
6309             (match_operand:V8HI 1 "register_operand" "x"))
6310           (ss_truncate:V8QI
6311             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))))]
6312   "TARGET_AVX"
6313   "vpacksswb\t{%2, %1, %0|%0, %1, %2}"
6314   [(set_attr "type" "sselog")
6315    (set_attr "prefix" "vex")
6316    (set_attr "mode" "TI")])
6317
6318 (define_insn "sse2_packsswb"
6319   [(set (match_operand:V16QI 0 "register_operand" "=x")
6320         (vec_concat:V16QI
6321           (ss_truncate:V8QI
6322             (match_operand:V8HI 1 "register_operand" "0"))
6323           (ss_truncate:V8QI
6324             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))))]
6325   "TARGET_SSE2"
6326   "packsswb\t{%2, %0|%0, %2}"
6327   [(set_attr "type" "sselog")
6328    (set_attr "prefix_data16" "1")
6329    (set_attr "mode" "TI")])
6330
6331 (define_insn "*avx_packssdw"
6332   [(set (match_operand:V8HI 0 "register_operand" "=x")
6333         (vec_concat:V8HI
6334           (ss_truncate:V4HI
6335             (match_operand:V4SI 1 "register_operand" "x"))
6336           (ss_truncate:V4HI
6337             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))))]
6338   "TARGET_AVX"
6339   "vpackssdw\t{%2, %1, %0|%0, %1, %2}"
6340   [(set_attr "type" "sselog")
6341    (set_attr "prefix" "vex")
6342    (set_attr "mode" "TI")])
6343
6344 (define_insn "sse2_packssdw"
6345   [(set (match_operand:V8HI 0 "register_operand" "=x")
6346         (vec_concat:V8HI
6347           (ss_truncate:V4HI
6348             (match_operand:V4SI 1 "register_operand" "0"))
6349           (ss_truncate:V4HI
6350             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))))]
6351   "TARGET_SSE2"
6352   "packssdw\t{%2, %0|%0, %2}"
6353   [(set_attr "type" "sselog")
6354    (set_attr "prefix_data16" "1")
6355    (set_attr "mode" "TI")])
6356
6357 (define_insn "*avx_packuswb"
6358   [(set (match_operand:V16QI 0 "register_operand" "=x")
6359         (vec_concat:V16QI
6360           (us_truncate:V8QI
6361             (match_operand:V8HI 1 "register_operand" "x"))
6362           (us_truncate:V8QI
6363             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))))]
6364   "TARGET_AVX"
6365   "vpackuswb\t{%2, %1, %0|%0, %1, %2}"
6366   [(set_attr "type" "sselog")
6367    (set_attr "prefix" "vex")
6368    (set_attr "mode" "TI")])
6369
6370 (define_insn "sse2_packuswb"
6371   [(set (match_operand:V16QI 0 "register_operand" "=x")
6372         (vec_concat:V16QI
6373           (us_truncate:V8QI
6374             (match_operand:V8HI 1 "register_operand" "0"))
6375           (us_truncate:V8QI
6376             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))))]
6377   "TARGET_SSE2"
6378   "packuswb\t{%2, %0|%0, %2}"
6379   [(set_attr "type" "sselog")
6380    (set_attr "prefix_data16" "1")
6381    (set_attr "mode" "TI")])
6382
6383 (define_insn "*avx_punpckhbw"
6384   [(set (match_operand:V16QI 0 "register_operand" "=x")
6385         (vec_select:V16QI
6386           (vec_concat:V32QI
6387             (match_operand:V16QI 1 "register_operand" "x")
6388             (match_operand:V16QI 2 "nonimmediate_operand" "xm"))
6389           (parallel [(const_int 8)  (const_int 24)
6390                      (const_int 9)  (const_int 25)
6391                      (const_int 10) (const_int 26)
6392                      (const_int 11) (const_int 27)
6393                      (const_int 12) (const_int 28)
6394                      (const_int 13) (const_int 29)
6395                      (const_int 14) (const_int 30)
6396                      (const_int 15) (const_int 31)])))]
6397   "TARGET_AVX"
6398   "vpunpckhbw\t{%2, %1, %0|%0, %1, %2}"
6399   [(set_attr "type" "sselog")
6400    (set_attr "prefix" "vex")
6401    (set_attr "mode" "TI")])
6402
6403 (define_insn "sse2_punpckhbw"
6404   [(set (match_operand:V16QI 0 "register_operand" "=x")
6405         (vec_select:V16QI
6406           (vec_concat:V32QI
6407             (match_operand:V16QI 1 "register_operand" "0")
6408             (match_operand:V16QI 2 "nonimmediate_operand" "xm"))
6409           (parallel [(const_int 8)  (const_int 24)
6410                      (const_int 9)  (const_int 25)
6411                      (const_int 10) (const_int 26)
6412                      (const_int 11) (const_int 27)
6413                      (const_int 12) (const_int 28)
6414                      (const_int 13) (const_int 29)
6415                      (const_int 14) (const_int 30)
6416                      (const_int 15) (const_int 31)])))]
6417   "TARGET_SSE2"
6418   "punpckhbw\t{%2, %0|%0, %2}"
6419   [(set_attr "type" "sselog")
6420    (set_attr "prefix_data16" "1")
6421    (set_attr "mode" "TI")])
6422
6423 (define_insn "*avx_punpcklbw"
6424   [(set (match_operand:V16QI 0 "register_operand" "=x")
6425         (vec_select:V16QI
6426           (vec_concat:V32QI
6427             (match_operand:V16QI 1 "register_operand" "x")
6428             (match_operand:V16QI 2 "nonimmediate_operand" "xm"))
6429           (parallel [(const_int 0) (const_int 16)
6430                      (const_int 1) (const_int 17)
6431                      (const_int 2) (const_int 18)
6432                      (const_int 3) (const_int 19)
6433                      (const_int 4) (const_int 20)
6434                      (const_int 5) (const_int 21)
6435                      (const_int 6) (const_int 22)
6436                      (const_int 7) (const_int 23)])))]
6437   "TARGET_AVX"
6438   "vpunpcklbw\t{%2, %1, %0|%0, %1, %2}"
6439   [(set_attr "type" "sselog")
6440    (set_attr "prefix" "vex")
6441    (set_attr "mode" "TI")])
6442
6443 (define_insn "sse2_punpcklbw"
6444   [(set (match_operand:V16QI 0 "register_operand" "=x")
6445         (vec_select:V16QI
6446           (vec_concat:V32QI
6447             (match_operand:V16QI 1 "register_operand" "0")
6448             (match_operand:V16QI 2 "nonimmediate_operand" "xm"))
6449           (parallel [(const_int 0) (const_int 16)
6450                      (const_int 1) (const_int 17)
6451                      (const_int 2) (const_int 18)
6452                      (const_int 3) (const_int 19)
6453                      (const_int 4) (const_int 20)
6454                      (const_int 5) (const_int 21)
6455                      (const_int 6) (const_int 22)
6456                      (const_int 7) (const_int 23)])))]
6457   "TARGET_SSE2"
6458   "punpcklbw\t{%2, %0|%0, %2}"
6459   [(set_attr "type" "sselog")
6460    (set_attr "prefix_data16" "1")
6461    (set_attr "mode" "TI")])
6462
6463 (define_insn "*avx_punpckhwd"
6464   [(set (match_operand:V8HI 0 "register_operand" "=x")
6465         (vec_select:V8HI
6466           (vec_concat:V16HI
6467             (match_operand:V8HI 1 "register_operand" "x")
6468             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
6469           (parallel [(const_int 4) (const_int 12)
6470                      (const_int 5) (const_int 13)
6471                      (const_int 6) (const_int 14)
6472                      (const_int 7) (const_int 15)])))]
6473   "TARGET_AVX"
6474   "vpunpckhwd\t{%2, %1, %0|%0, %1, %2}"
6475   [(set_attr "type" "sselog")
6476    (set_attr "prefix" "vex")
6477    (set_attr "mode" "TI")])
6478
6479 (define_insn "sse2_punpckhwd"
6480   [(set (match_operand:V8HI 0 "register_operand" "=x")
6481         (vec_select:V8HI
6482           (vec_concat:V16HI
6483             (match_operand:V8HI 1 "register_operand" "0")
6484             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
6485           (parallel [(const_int 4) (const_int 12)
6486                      (const_int 5) (const_int 13)
6487                      (const_int 6) (const_int 14)
6488                      (const_int 7) (const_int 15)])))]
6489   "TARGET_SSE2"
6490   "punpckhwd\t{%2, %0|%0, %2}"
6491   [(set_attr "type" "sselog")
6492    (set_attr "prefix_data16" "1")
6493    (set_attr "mode" "TI")])
6494
6495 (define_insn "*avx_punpcklwd"
6496   [(set (match_operand:V8HI 0 "register_operand" "=x")
6497         (vec_select:V8HI
6498           (vec_concat:V16HI
6499             (match_operand:V8HI 1 "register_operand" "x")
6500             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
6501           (parallel [(const_int 0) (const_int 8)
6502                      (const_int 1) (const_int 9)
6503                      (const_int 2) (const_int 10)
6504                      (const_int 3) (const_int 11)])))]
6505   "TARGET_AVX"
6506   "vpunpcklwd\t{%2, %1, %0|%0, %1, %2}"
6507   [(set_attr "type" "sselog")
6508    (set_attr "prefix" "vex")
6509    (set_attr "mode" "TI")])
6510
6511 (define_insn "sse2_punpcklwd"
6512   [(set (match_operand:V8HI 0 "register_operand" "=x")
6513         (vec_select:V8HI
6514           (vec_concat:V16HI
6515             (match_operand:V8HI 1 "register_operand" "0")
6516             (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
6517           (parallel [(const_int 0) (const_int 8)
6518                      (const_int 1) (const_int 9)
6519                      (const_int 2) (const_int 10)
6520                      (const_int 3) (const_int 11)])))]
6521   "TARGET_SSE2"
6522   "punpcklwd\t{%2, %0|%0, %2}"
6523   [(set_attr "type" "sselog")
6524    (set_attr "prefix_data16" "1")
6525    (set_attr "mode" "TI")])
6526
6527 (define_insn "*avx_punpckhdq"
6528   [(set (match_operand:V4SI 0 "register_operand" "=x")
6529         (vec_select:V4SI
6530           (vec_concat:V8SI
6531             (match_operand:V4SI 1 "register_operand" "x")
6532             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
6533           (parallel [(const_int 2) (const_int 6)
6534                      (const_int 3) (const_int 7)])))]
6535   "TARGET_AVX"
6536   "vpunpckhdq\t{%2, %1, %0|%0, %1, %2}"
6537   [(set_attr "type" "sselog")
6538    (set_attr "prefix" "vex")
6539    (set_attr "mode" "TI")])
6540
6541 (define_insn "sse2_punpckhdq"
6542   [(set (match_operand:V4SI 0 "register_operand" "=x")
6543         (vec_select:V4SI
6544           (vec_concat:V8SI
6545             (match_operand:V4SI 1 "register_operand" "0")
6546             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
6547           (parallel [(const_int 2) (const_int 6)
6548                      (const_int 3) (const_int 7)])))]
6549   "TARGET_SSE2"
6550   "punpckhdq\t{%2, %0|%0, %2}"
6551   [(set_attr "type" "sselog")
6552    (set_attr "prefix_data16" "1")
6553    (set_attr "mode" "TI")])
6554
6555 (define_insn "*avx_punpckldq"
6556   [(set (match_operand:V4SI 0 "register_operand" "=x")
6557         (vec_select:V4SI
6558           (vec_concat:V8SI
6559             (match_operand:V4SI 1 "register_operand" "x")
6560             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
6561           (parallel [(const_int 0) (const_int 4)
6562                      (const_int 1) (const_int 5)])))]
6563   "TARGET_AVX"
6564   "vpunpckldq\t{%2, %1, %0|%0, %1, %2}"
6565   [(set_attr "type" "sselog")
6566    (set_attr "prefix" "vex")
6567    (set_attr "mode" "TI")])
6568
6569 (define_insn "sse2_punpckldq"
6570   [(set (match_operand:V4SI 0 "register_operand" "=x")
6571         (vec_select:V4SI
6572           (vec_concat:V8SI
6573             (match_operand:V4SI 1 "register_operand" "0")
6574             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
6575           (parallel [(const_int 0) (const_int 4)
6576                      (const_int 1) (const_int 5)])))]
6577   "TARGET_SSE2"
6578   "punpckldq\t{%2, %0|%0, %2}"
6579   [(set_attr "type" "sselog")
6580    (set_attr "prefix_data16" "1")
6581    (set_attr "mode" "TI")])
6582
6583 (define_insn "*avx_pinsr<avxmodesuffixs>"
6584   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
6585         (vec_merge:SSEMODE124
6586           (vec_duplicate:SSEMODE124
6587             (match_operand:<avxscalarmode> 2 "nonimmediate_operand" "rm"))
6588           (match_operand:SSEMODE124 1 "register_operand" "x")
6589           (match_operand:SI 3 "const_pow2_1_to_<pinsrbits>_operand" "n")))]
6590   "TARGET_AVX"
6591 {
6592   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6593   if (MEM_P (operands[2]))
6594     return "vpinsr<avxmodesuffixs>\t{%3, %2, %1, %0|%0, %1, %2, %3}";
6595   else
6596     return "vpinsr<avxmodesuffixs>\t{%3, %k2, %1, %0|%0, %1, %k2, %3}";
6597 }
6598   [(set_attr "type" "sselog")
6599    (set_attr "prefix" "vex")
6600    (set_attr "mode" "TI")])
6601
6602 (define_insn "*sse4_1_pinsrb"
6603   [(set (match_operand:V16QI 0 "register_operand" "=x")
6604         (vec_merge:V16QI
6605           (vec_duplicate:V16QI
6606             (match_operand:QI 2 "nonimmediate_operand" "rm"))
6607           (match_operand:V16QI 1 "register_operand" "0")
6608           (match_operand:SI 3 "const_pow2_1_to_32768_operand" "n")))]
6609   "TARGET_SSE4_1"
6610 {
6611   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6612   if (MEM_P (operands[2]))
6613     return "pinsrb\t{%3, %2, %0|%0, %2, %3}";
6614   else
6615     return "pinsrb\t{%3, %k2, %0|%0, %k2, %3}";
6616 }
6617   [(set_attr "type" "sselog")
6618    (set_attr "prefix_extra" "1")
6619    (set_attr "mode" "TI")])
6620
6621 (define_insn "*sse2_pinsrw"
6622   [(set (match_operand:V8HI 0 "register_operand" "=x")
6623         (vec_merge:V8HI
6624           (vec_duplicate:V8HI
6625             (match_operand:HI 2 "nonimmediate_operand" "rm"))
6626           (match_operand:V8HI 1 "register_operand" "0")
6627           (match_operand:SI 3 "const_pow2_1_to_128_operand" "n")))]
6628   "TARGET_SSE2"
6629 {
6630   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6631   if (MEM_P (operands[2]))
6632     return "pinsrw\t{%3, %2, %0|%0, %2, %3}";
6633   else
6634     return "pinsrw\t{%3, %k2, %0|%0, %k2, %3}";
6635 }
6636   [(set_attr "type" "sselog")
6637    (set_attr "prefix_data16" "1")
6638    (set_attr "mode" "TI")])
6639
6640 ;; It must come before sse2_loadld since it is preferred.
6641 (define_insn "*sse4_1_pinsrd"
6642   [(set (match_operand:V4SI 0 "register_operand" "=x")
6643         (vec_merge:V4SI
6644           (vec_duplicate:V4SI
6645             (match_operand:SI 2 "nonimmediate_operand" "rm"))
6646           (match_operand:V4SI 1 "register_operand" "0")
6647           (match_operand:SI 3 "const_pow2_1_to_8_operand" "n")))]
6648   "TARGET_SSE4_1"
6649 {
6650   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6651   return "pinsrd\t{%3, %2, %0|%0, %2, %3}";
6652 }
6653   [(set_attr "type" "sselog")
6654    (set_attr "prefix_extra" "1")
6655    (set_attr "mode" "TI")])
6656
6657 (define_insn "*avx_pinsrq"
6658   [(set (match_operand:V2DI 0 "register_operand" "=x")
6659         (vec_merge:V2DI
6660           (vec_duplicate:V2DI
6661             (match_operand:DI 2 "nonimmediate_operand" "rm"))
6662           (match_operand:V2DI 1 "register_operand" "x")
6663           (match_operand:SI 3 "const_pow2_1_to_2_operand" "n")))]
6664   "TARGET_AVX && TARGET_64BIT"
6665 {
6666   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6667   return "vpinsrq\t{%3, %2, %1, %0|%0, %1, %2, %3}";
6668 }
6669   [(set_attr "type" "sselog")
6670    (set_attr "prefix" "vex")
6671    (set_attr "mode" "TI")])
6672
6673 (define_insn "*sse4_1_pinsrq"
6674   [(set (match_operand:V2DI 0 "register_operand" "=x")
6675         (vec_merge:V2DI
6676           (vec_duplicate:V2DI
6677             (match_operand:DI 2 "nonimmediate_operand" "rm"))
6678           (match_operand:V2DI 1 "register_operand" "0")
6679           (match_operand:SI 3 "const_pow2_1_to_2_operand" "n")))]
6680   "TARGET_SSE4_1 && TARGET_64BIT"
6681 {
6682   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6683   return "pinsrq\t{%3, %2, %0|%0, %2, %3}";
6684 }
6685   [(set_attr "type" "sselog")
6686    (set_attr "prefix_extra" "1")
6687    (set_attr "mode" "TI")])
6688
6689 (define_insn "*sse4_1_pextrb"
6690   [(set (match_operand:SI 0 "register_operand" "=r")
6691         (zero_extend:SI
6692           (vec_select:QI
6693             (match_operand:V16QI 1 "register_operand" "x")
6694             (parallel [(match_operand:SI 2 "const_0_to_15_operand" "n")]))))]
6695   "TARGET_SSE4_1"
6696   "%vpextrb\t{%2, %1, %0|%0, %1, %2}"
6697   [(set_attr "type" "sselog")
6698    (set_attr "prefix_extra" "1")
6699    (set_attr "prefix" "maybe_vex")
6700    (set_attr "mode" "TI")])
6701
6702 (define_insn "*sse4_1_pextrb_memory"
6703   [(set (match_operand:QI 0 "memory_operand" "=m")
6704         (vec_select:QI
6705           (match_operand:V16QI 1 "register_operand" "x")
6706           (parallel [(match_operand:SI 2 "const_0_to_15_operand" "n")])))]
6707   "TARGET_SSE4_1"
6708   "%vpextrb\t{%2, %1, %0|%0, %1, %2}"
6709   [(set_attr "type" "sselog")
6710    (set_attr "prefix_extra" "1")
6711    (set_attr "prefix" "maybe_vex")
6712    (set_attr "mode" "TI")])
6713
6714 (define_insn "*sse2_pextrw"
6715   [(set (match_operand:SI 0 "register_operand" "=r")
6716         (zero_extend:SI
6717           (vec_select:HI
6718             (match_operand:V8HI 1 "register_operand" "x")
6719             (parallel [(match_operand:SI 2 "const_0_to_7_operand" "n")]))))]
6720   "TARGET_SSE2"
6721   "%vpextrw\t{%2, %1, %0|%0, %1, %2}"
6722   [(set_attr "type" "sselog")
6723    (set_attr "prefix_data16" "1")
6724    (set_attr "prefix" "maybe_vex")
6725    (set_attr "mode" "TI")])
6726
6727 (define_insn "*sse4_1_pextrw_memory"
6728   [(set (match_operand:HI 0 "memory_operand" "=m")
6729         (vec_select:HI
6730           (match_operand:V8HI 1 "register_operand" "x")
6731           (parallel [(match_operand:SI 2 "const_0_to_7_operand" "n")])))]
6732   "TARGET_SSE4_1"
6733   "%vpextrw\t{%2, %1, %0|%0, %1, %2}"
6734   [(set_attr "type" "sselog")
6735    (set_attr "prefix_extra" "1")
6736    (set_attr "prefix" "maybe_vex")
6737    (set_attr "mode" "TI")])
6738
6739 (define_insn "*sse4_1_pextrd"
6740   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
6741         (vec_select:SI
6742           (match_operand:V4SI 1 "register_operand" "x")
6743           (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n")])))]
6744   "TARGET_SSE4_1"
6745   "%vpextrd\t{%2, %1, %0|%0, %1, %2}"
6746   [(set_attr "type" "sselog")
6747    (set_attr "prefix_extra" "1")
6748    (set_attr "prefix" "maybe_vex")
6749    (set_attr "mode" "TI")])
6750
6751 ;; It must come before *vec_extractv2di_1_sse since it is preferred.
6752 (define_insn "*sse4_1_pextrq"
6753   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
6754         (vec_select:DI
6755           (match_operand:V2DI 1 "register_operand" "x")
6756           (parallel [(match_operand:SI 2 "const_0_to_1_operand" "n")])))]
6757   "TARGET_SSE4_1 && TARGET_64BIT"
6758   "%vpextrq\t{%2, %1, %0|%0, %1, %2}"
6759   [(set_attr "type" "sselog")
6760    (set_attr "prefix_extra" "1")
6761    (set_attr "prefix" "maybe_vex")
6762    (set_attr "mode" "TI")])
6763
6764 (define_expand "sse2_pshufd"
6765   [(match_operand:V4SI 0 "register_operand" "")
6766    (match_operand:V4SI 1 "nonimmediate_operand" "")
6767    (match_operand:SI 2 "const_int_operand" "")]
6768   "TARGET_SSE2"
6769 {
6770   int mask = INTVAL (operands[2]);
6771   emit_insn (gen_sse2_pshufd_1 (operands[0], operands[1],
6772                                 GEN_INT ((mask >> 0) & 3),
6773                                 GEN_INT ((mask >> 2) & 3),
6774                                 GEN_INT ((mask >> 4) & 3),
6775                                 GEN_INT ((mask >> 6) & 3)));
6776   DONE;
6777 })
6778
6779 (define_insn "sse2_pshufd_1"
6780   [(set (match_operand:V4SI 0 "register_operand" "=x")
6781         (vec_select:V4SI
6782           (match_operand:V4SI 1 "nonimmediate_operand" "xm")
6783           (parallel [(match_operand 2 "const_0_to_3_operand" "")
6784                      (match_operand 3 "const_0_to_3_operand" "")
6785                      (match_operand 4 "const_0_to_3_operand" "")
6786                      (match_operand 5 "const_0_to_3_operand" "")])))]
6787   "TARGET_SSE2"
6788 {
6789   int mask = 0;
6790   mask |= INTVAL (operands[2]) << 0;
6791   mask |= INTVAL (operands[3]) << 2;
6792   mask |= INTVAL (operands[4]) << 4;
6793   mask |= INTVAL (operands[5]) << 6;
6794   operands[2] = GEN_INT (mask);
6795
6796   return "%vpshufd\t{%2, %1, %0|%0, %1, %2}";
6797 }
6798   [(set_attr "type" "sselog1")
6799    (set_attr "prefix_data16" "1")
6800    (set_attr "prefix" "vex")
6801    (set_attr "mode" "TI")])
6802
6803 (define_expand "sse2_pshuflw"
6804   [(match_operand:V8HI 0 "register_operand" "")
6805    (match_operand:V8HI 1 "nonimmediate_operand" "")
6806    (match_operand:SI 2 "const_int_operand" "")]
6807   "TARGET_SSE2"
6808 {
6809   int mask = INTVAL (operands[2]);
6810   emit_insn (gen_sse2_pshuflw_1 (operands[0], operands[1],
6811                                  GEN_INT ((mask >> 0) & 3),
6812                                  GEN_INT ((mask >> 2) & 3),
6813                                  GEN_INT ((mask >> 4) & 3),
6814                                  GEN_INT ((mask >> 6) & 3)));
6815   DONE;
6816 })
6817
6818 (define_insn "sse2_pshuflw_1"
6819   [(set (match_operand:V8HI 0 "register_operand" "=x")
6820         (vec_select:V8HI
6821           (match_operand:V8HI 1 "nonimmediate_operand" "xm")
6822           (parallel [(match_operand 2 "const_0_to_3_operand" "")
6823                      (match_operand 3 "const_0_to_3_operand" "")
6824                      (match_operand 4 "const_0_to_3_operand" "")
6825                      (match_operand 5 "const_0_to_3_operand" "")
6826                      (const_int 4)
6827                      (const_int 5)
6828                      (const_int 6)
6829                      (const_int 7)])))]
6830   "TARGET_SSE2"
6831 {
6832   int mask = 0;
6833   mask |= INTVAL (operands[2]) << 0;
6834   mask |= INTVAL (operands[3]) << 2;
6835   mask |= INTVAL (operands[4]) << 4;
6836   mask |= INTVAL (operands[5]) << 6;
6837   operands[2] = GEN_INT (mask);
6838
6839   return "%vpshuflw\t{%2, %1, %0|%0, %1, %2}";
6840 }
6841   [(set_attr "type" "sselog")
6842    (set_attr "prefix_rep" "1")
6843    (set_attr "prefix" "maybe_vex")
6844    (set_attr "mode" "TI")])
6845
6846 (define_expand "sse2_pshufhw"
6847   [(match_operand:V8HI 0 "register_operand" "")
6848    (match_operand:V8HI 1 "nonimmediate_operand" "")
6849    (match_operand:SI 2 "const_int_operand" "")]
6850   "TARGET_SSE2"
6851 {
6852   int mask = INTVAL (operands[2]);
6853   emit_insn (gen_sse2_pshufhw_1 (operands[0], operands[1],
6854                                  GEN_INT (((mask >> 0) & 3) + 4),
6855                                  GEN_INT (((mask >> 2) & 3) + 4),
6856                                  GEN_INT (((mask >> 4) & 3) + 4),
6857                                  GEN_INT (((mask >> 6) & 3) + 4)));
6858   DONE;
6859 })
6860
6861 (define_insn "sse2_pshufhw_1"
6862   [(set (match_operand:V8HI 0 "register_operand" "=x")
6863         (vec_select:V8HI
6864           (match_operand:V8HI 1 "nonimmediate_operand" "xm")
6865           (parallel [(const_int 0)
6866                      (const_int 1)
6867                      (const_int 2)
6868                      (const_int 3)
6869                      (match_operand 2 "const_4_to_7_operand" "")
6870                      (match_operand 3 "const_4_to_7_operand" "")
6871                      (match_operand 4 "const_4_to_7_operand" "")
6872                      (match_operand 5 "const_4_to_7_operand" "")])))]
6873   "TARGET_SSE2"
6874 {
6875   int mask = 0;
6876   mask |= (INTVAL (operands[2]) - 4) << 0;
6877   mask |= (INTVAL (operands[3]) - 4) << 2;
6878   mask |= (INTVAL (operands[4]) - 4) << 4;
6879   mask |= (INTVAL (operands[5]) - 4) << 6;
6880   operands[2] = GEN_INT (mask);
6881
6882   return "%vpshufhw\t{%2, %1, %0|%0, %1, %2}";
6883 }
6884   [(set_attr "type" "sselog")
6885    (set_attr "prefix_rep" "1")
6886    (set_attr "prefix" "maybe_vex")
6887    (set_attr "mode" "TI")])
6888
6889 (define_expand "sse2_loadd"
6890   [(set (match_operand:V4SI 0 "register_operand" "")
6891         (vec_merge:V4SI
6892           (vec_duplicate:V4SI
6893             (match_operand:SI 1 "nonimmediate_operand" ""))
6894           (match_dup 2)
6895           (const_int 1)))]
6896   "TARGET_SSE"
6897   "operands[2] = CONST0_RTX (V4SImode);")
6898
6899 (define_insn "*avx_loadld"
6900   [(set (match_operand:V4SI 0 "register_operand"       "=x,Yi,x")
6901         (vec_merge:V4SI
6902           (vec_duplicate:V4SI
6903             (match_operand:SI 2 "nonimmediate_operand" "m ,r ,x"))
6904           (match_operand:V4SI 1 "reg_or_0_operand"     "C ,C ,x")
6905           (const_int 1)))]
6906   "TARGET_AVX"
6907   "@
6908    vmovd\t{%2, %0|%0, %2}
6909    vmovd\t{%2, %0|%0, %2}
6910    vmovss\t{%2, %1, %0|%0, %1, %2}"
6911   [(set_attr "type" "ssemov")
6912    (set_attr "prefix" "vex")
6913    (set_attr "mode" "TI,TI,V4SF")])
6914
6915 (define_insn "sse2_loadld"
6916   [(set (match_operand:V4SI 0 "register_operand"       "=Y2,Yi,x,x")
6917         (vec_merge:V4SI
6918           (vec_duplicate:V4SI
6919             (match_operand:SI 2 "nonimmediate_operand" "m  ,r ,m,x"))
6920           (match_operand:V4SI 1 "reg_or_0_operand"     "C  ,C ,C,0")
6921           (const_int 1)))]
6922   "TARGET_SSE"
6923   "@
6924    movd\t{%2, %0|%0, %2}
6925    movd\t{%2, %0|%0, %2}
6926    movss\t{%2, %0|%0, %2}
6927    movss\t{%2, %0|%0, %2}"
6928   [(set_attr "type" "ssemov")
6929    (set_attr "mode" "TI,TI,V4SF,SF")])
6930
6931 (define_insn_and_split "sse2_stored"
6932   [(set (match_operand:SI 0 "nonimmediate_operand" "=mx,r")
6933         (vec_select:SI
6934           (match_operand:V4SI 1 "register_operand" "x,Yi")
6935           (parallel [(const_int 0)])))]
6936   "TARGET_SSE"
6937   "#"
6938   "&& reload_completed
6939    && (TARGET_INTER_UNIT_MOVES
6940        || MEM_P (operands [0])
6941        || !GENERAL_REGNO_P (true_regnum (operands [0])))"
6942   [(set (match_dup 0) (match_dup 1))]
6943 {
6944   operands[1] = gen_rtx_REG (SImode, REGNO (operands[1]));
6945 })
6946
6947 (define_insn_and_split "*vec_ext_v4si_mem"
6948   [(set (match_operand:SI 0 "register_operand" "=r")
6949         (vec_select:SI
6950           (match_operand:V4SI 1 "memory_operand" "o")
6951           (parallel [(match_operand 2 "const_0_to_3_operand" "")])))]
6952   ""
6953   "#"
6954   "reload_completed"
6955   [(const_int 0)]
6956 {
6957   int i = INTVAL (operands[2]);
6958
6959   emit_move_insn (operands[0], adjust_address (operands[1], SImode, i*4));
6960   DONE;
6961 })
6962
6963 (define_expand "sse_storeq"
6964   [(set (match_operand:DI 0 "nonimmediate_operand" "")
6965         (vec_select:DI
6966           (match_operand:V2DI 1 "register_operand" "")
6967           (parallel [(const_int 0)])))]
6968   "TARGET_SSE"
6969   "")
6970
6971 (define_insn "*sse2_storeq_rex64"
6972   [(set (match_operand:DI 0 "nonimmediate_operand" "=mx,*r,r")
6973         (vec_select:DI
6974           (match_operand:V2DI 1 "nonimmediate_operand" "x,Yi,o")
6975           (parallel [(const_int 0)])))]
6976   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6977   "@
6978    #
6979    #
6980    %vmov{q}\t{%1, %0|%0, %1}"
6981   [(set_attr "type" "*,*,imov")
6982    (set_attr "prefix" "*,*,maybe_vex")
6983    (set_attr "mode" "*,*,DI")])
6984
6985 (define_insn "*sse2_storeq"
6986   [(set (match_operand:DI 0 "nonimmediate_operand" "=mx")
6987         (vec_select:DI
6988           (match_operand:V2DI 1 "register_operand" "x")
6989           (parallel [(const_int 0)])))]
6990   "TARGET_SSE"
6991   "#")
6992
6993 (define_split
6994   [(set (match_operand:DI 0 "nonimmediate_operand" "")
6995         (vec_select:DI
6996           (match_operand:V2DI 1 "register_operand" "")
6997           (parallel [(const_int 0)])))]
6998   "TARGET_SSE
6999    && reload_completed
7000    && (TARGET_INTER_UNIT_MOVES
7001        || MEM_P (operands [0])
7002        || !GENERAL_REGNO_P (true_regnum (operands [0])))"
7003   [(set (match_dup 0) (match_dup 1))]
7004 {
7005   operands[1] = gen_rtx_REG (DImode, REGNO (operands[1]));
7006 })
7007
7008 (define_insn "*vec_extractv2di_1_rex64_avx"
7009   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,x,x,r")
7010         (vec_select:DI
7011           (match_operand:V2DI 1 "nonimmediate_operand" "x,x,o,o")
7012           (parallel [(const_int 1)])))]
7013   "TARGET_64BIT
7014    && TARGET_AVX
7015    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7016   "@
7017    vmovhps\t{%1, %0|%0, %1}
7018    vpsrldq\t{$8, %1, %0|%0, %1, 8}
7019    vmovq\t{%H1, %0|%0, %H1}
7020    vmov{q}\t{%H1, %0|%0, %H1}"
7021   [(set_attr "type" "ssemov,sseishft,ssemov,imov")
7022    (set_attr "memory" "*,none,*,*")
7023    (set_attr "prefix" "vex")
7024    (set_attr "mode" "V2SF,TI,TI,DI")])
7025
7026 (define_insn "*vec_extractv2di_1_rex64"
7027   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,x,x,r")
7028         (vec_select:DI
7029           (match_operand:V2DI 1 "nonimmediate_operand" "x,0,o,o")
7030           (parallel [(const_int 1)])))]
7031   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7032   "@
7033    movhps\t{%1, %0|%0, %1}
7034    psrldq\t{$8, %0|%0, 8}
7035    movq\t{%H1, %0|%0, %H1}
7036    mov{q}\t{%H1, %0|%0, %H1}"
7037   [(set_attr "type" "ssemov,sseishft,ssemov,imov")
7038    (set_attr "memory" "*,none,*,*")
7039    (set_attr "mode" "V2SF,TI,TI,DI")])
7040
7041 (define_insn "*vec_extractv2di_1_avx"
7042   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,x,x")
7043         (vec_select:DI
7044           (match_operand:V2DI 1 "nonimmediate_operand" "x,x,o")
7045           (parallel [(const_int 1)])))]
7046   "!TARGET_64BIT
7047    && TARGET_AVX
7048    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7049   "@
7050    vmovhps\t{%1, %0|%0, %1}
7051    vpsrldq\t{$8, %1, %0|%0, %1, 8}
7052    vmovq\t{%H1, %0|%0, %H1}"
7053   [(set_attr "type" "ssemov,sseishft,ssemov")
7054    (set_attr "memory" "*,none,*")
7055    (set_attr "prefix" "vex")
7056    (set_attr "mode" "V2SF,TI,TI")])
7057
7058 (define_insn "*vec_extractv2di_1_sse2"
7059   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,x,x")
7060         (vec_select:DI
7061           (match_operand:V2DI 1 "nonimmediate_operand" "x,0,o")
7062           (parallel [(const_int 1)])))]
7063   "!TARGET_64BIT
7064    && TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7065   "@
7066    movhps\t{%1, %0|%0, %1}
7067    psrldq\t{$8, %0|%0, 8}
7068    movq\t{%H1, %0|%0, %H1}"
7069   [(set_attr "type" "ssemov,sseishft,ssemov")
7070    (set_attr "memory" "*,none,*")
7071    (set_attr "mode" "V2SF,TI,TI")])
7072
7073 ;; Not sure this is ever used, but it doesn't hurt to have it. -aoliva
7074 (define_insn "*vec_extractv2di_1_sse"
7075   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,x,x")
7076         (vec_select:DI
7077           (match_operand:V2DI 1 "nonimmediate_operand" "x,x,o")
7078           (parallel [(const_int 1)])))]
7079   "!TARGET_SSE2 && TARGET_SSE
7080    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7081   "@
7082    movhps\t{%1, %0|%0, %1}
7083    movhlps\t{%1, %0|%0, %1}
7084    movlps\t{%H1, %0|%0, %H1}"
7085   [(set_attr "type" "ssemov")
7086    (set_attr "mode" "V2SF,V4SF,V2SF")])
7087
7088 (define_insn "*vec_dupv4si"
7089   [(set (match_operand:V4SI 0 "register_operand" "=Y2,x")
7090         (vec_duplicate:V4SI
7091           (match_operand:SI 1 "register_operand" " Y2,0")))]
7092   "TARGET_SSE"
7093   "@
7094    %vpshufd\t{$0, %1, %0|%0, %1, 0}
7095    shufps\t{$0, %0, %0|%0, %0, 0}"
7096   [(set_attr "type" "sselog1")
7097    (set_attr "prefix" "maybe_vex,orig")
7098    (set_attr "mode" "TI,V4SF")])
7099
7100 (define_insn "*vec_dupv2di_avx"
7101   [(set (match_operand:V2DI 0 "register_operand" "=x")
7102         (vec_duplicate:V2DI
7103           (match_operand:DI 1 "register_operand" "x")))]
7104   "TARGET_AVX"
7105   "vpunpcklqdq\t{%1, %1, %0|%0, %1, %1}"
7106   [(set_attr "type" "sselog1")
7107    (set_attr "prefix" "vex")
7108    (set_attr "mode" "TI")])
7109
7110 (define_insn "*vec_dupv2di"
7111   [(set (match_operand:V2DI 0 "register_operand" "=Y2,x")
7112         (vec_duplicate:V2DI
7113           (match_operand:DI 1 "register_operand" " 0 ,0")))]
7114   "TARGET_SSE"
7115   "@
7116    punpcklqdq\t%0, %0
7117    movlhps\t%0, %0"
7118   [(set_attr "type" "sselog1,ssemov")
7119    (set_attr "mode" "TI,V4SF")])
7120
7121 (define_insn "*vec_concatv2si_avx"
7122   [(set (match_operand:V2SI 0 "register_operand"     "=x,x,x ,*y ,*y")
7123         (vec_concat:V2SI
7124           (match_operand:SI 1 "nonimmediate_operand" "x ,x,rm, 0 ,rm")
7125           (match_operand:SI 2 "vector_move_operand"  "rm,x,C ,*ym,C")))]
7126   "TARGET_AVX"
7127   "@
7128    vpinsrd\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}
7129    vpunpckldq\t{%2, %1, %0|%0, %1, %2}
7130    vmovd\t{%1, %0|%0, %1}
7131    punpckldq\t{%2, %0|%0, %2}
7132    movd\t{%1, %0|%0, %1}"
7133   [(set_attr "type" "sselog,sselog,ssemov,mmxcvt,mmxmov")
7134    (set (attr "prefix")
7135      (if_then_else (eq_attr "alternative" "3,4")
7136        (const_string "orig")
7137        (const_string "vex")))
7138    (set_attr "mode" "TI,TI,TI,DI,DI")])
7139
7140 (define_insn "*vec_concatv2si_sse4_1"
7141   [(set (match_operand:V2SI 0 "register_operand"     "=x,x,x ,*y ,*y")
7142         (vec_concat:V2SI
7143           (match_operand:SI 1 "nonimmediate_operand" "0 ,0,rm, 0 ,rm")
7144           (match_operand:SI 2 "vector_move_operand"  "rm,x,C ,*ym,C")))]
7145   "TARGET_SSE4_1"
7146   "@
7147    pinsrd\t{$0x1, %2, %0|%0, %2, 0x1}
7148    punpckldq\t{%2, %0|%0, %2}
7149    movd\t{%1, %0|%0, %1}
7150    punpckldq\t{%2, %0|%0, %2}
7151    movd\t{%1, %0|%0, %1}"
7152   [(set_attr "type" "sselog,sselog,ssemov,mmxcvt,mmxmov")
7153    (set_attr "prefix_extra" "1,*,*,*,*")
7154    (set_attr "mode" "TI,TI,TI,DI,DI")])
7155
7156 ;; ??? In theory we can match memory for the MMX alternative, but allowing
7157 ;; nonimmediate_operand for operand 2 and *not* allowing memory for the SSE
7158 ;; alternatives pretty much forces the MMX alternative to be chosen.
7159 (define_insn "*vec_concatv2si_sse2"
7160   [(set (match_operand:V2SI 0 "register_operand"     "=x,x ,*y,*y")
7161         (vec_concat:V2SI
7162           (match_operand:SI 1 "nonimmediate_operand" " 0,rm, 0,rm")
7163           (match_operand:SI 2 "reg_or_0_operand"     " x,C ,*y, C")))]
7164   "TARGET_SSE2"
7165   "@
7166    punpckldq\t{%2, %0|%0, %2}
7167    movd\t{%1, %0|%0, %1}
7168    punpckldq\t{%2, %0|%0, %2}
7169    movd\t{%1, %0|%0, %1}"
7170   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
7171    (set_attr "mode" "TI,TI,DI,DI")])
7172
7173 (define_insn "*vec_concatv2si_sse"
7174   [(set (match_operand:V2SI 0 "register_operand"     "=x,x,*y,*y")
7175         (vec_concat:V2SI
7176           (match_operand:SI 1 "nonimmediate_operand" " 0,m, 0,*rm")
7177           (match_operand:SI 2 "reg_or_0_operand"     " x,C,*y,C")))]
7178   "TARGET_SSE"
7179   "@
7180    unpcklps\t{%2, %0|%0, %2}
7181    movss\t{%1, %0|%0, %1}
7182    punpckldq\t{%2, %0|%0, %2}
7183    movd\t{%1, %0|%0, %1}"
7184   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
7185    (set_attr "mode" "V4SF,V4SF,DI,DI")])
7186
7187 (define_insn "*vec_concatv4si_1_avx"
7188   [(set (match_operand:V4SI 0 "register_operand"       "=x,x")
7189         (vec_concat:V4SI
7190           (match_operand:V2SI 1 "register_operand"     " x,x")
7191           (match_operand:V2SI 2 "nonimmediate_operand" " x,m")))]
7192   "TARGET_AVX"
7193   "@
7194    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7195    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7196   [(set_attr "type" "sselog,ssemov")
7197    (set_attr "prefix" "vex")
7198    (set_attr "mode" "TI,V2SF")])
7199
7200 (define_insn "*vec_concatv4si_1"
7201   [(set (match_operand:V4SI 0 "register_operand"       "=Y2,x,x")
7202         (vec_concat:V4SI
7203           (match_operand:V2SI 1 "register_operand"     " 0 ,0,0")
7204           (match_operand:V2SI 2 "nonimmediate_operand" " Y2,x,m")))]
7205   "TARGET_SSE"
7206   "@
7207    punpcklqdq\t{%2, %0|%0, %2}
7208    movlhps\t{%2, %0|%0, %2}
7209    movhps\t{%2, %0|%0, %2}"
7210   [(set_attr "type" "sselog,ssemov,ssemov")
7211    (set_attr "mode" "TI,V4SF,V2SF")])
7212
7213 (define_insn "*vec_concatv2di_avx"
7214   [(set (match_operand:V2DI 0 "register_operand"     "=x,?x,x,x")
7215         (vec_concat:V2DI
7216           (match_operand:DI 1 "nonimmediate_operand" " m,*y,x,x")
7217           (match_operand:DI 2 "vector_move_operand"  " C, C,x,m")))]
7218   "!TARGET_64BIT && TARGET_AVX"
7219   "@
7220    vmovq\t{%1, %0|%0, %1}
7221    movq2dq\t{%1, %0|%0, %1}
7222    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7223    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7224   [(set_attr "type" "ssemov,ssemov,sselog,ssemov")
7225    (set (attr "prefix")
7226      (if_then_else (eq_attr "alternative" "1")
7227        (const_string "orig")
7228        (const_string "vex")))
7229    (set_attr "mode" "TI,TI,TI,V2SF")])
7230
7231 (define_insn "vec_concatv2di"
7232   [(set (match_operand:V2DI 0 "register_operand"     "=Y2 ,?Y2,Y2,x,x")
7233         (vec_concat:V2DI
7234           (match_operand:DI 1 "nonimmediate_operand" " mY2,*y ,0 ,0,0")
7235           (match_operand:DI 2 "vector_move_operand"  " C  ,  C,Y2,x,m")))]
7236   "!TARGET_64BIT && TARGET_SSE"
7237   "@
7238    movq\t{%1, %0|%0, %1}
7239    movq2dq\t{%1, %0|%0, %1}
7240    punpcklqdq\t{%2, %0|%0, %2}
7241    movlhps\t{%2, %0|%0, %2}
7242    movhps\t{%2, %0|%0, %2}"
7243   [(set_attr "type" "ssemov,ssemov,sselog,ssemov,ssemov")
7244    (set_attr "mode" "TI,TI,TI,V4SF,V2SF")])
7245
7246 (define_insn "*vec_concatv2di_rex64_avx"
7247   [(set (match_operand:V2DI 0 "register_operand"     "=x,x,Yi,!x,x,x")
7248         (vec_concat:V2DI
7249           (match_operand:DI 1 "nonimmediate_operand" " x,m,r ,*y,x,x")
7250           (match_operand:DI 2 "vector_move_operand"  "rm,C,C ,C ,x,m")))]
7251   "TARGET_64BIT && TARGET_AVX"
7252   "@
7253    vpinsrq\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}
7254    vmovq\t{%1, %0|%0, %1}
7255    vmovq\t{%1, %0|%0, %1}
7256    movq2dq\t{%1, %0|%0, %1}
7257    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7258    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7259   [(set_attr "type" "sselog,ssemov,ssemov,ssemov,sselog,ssemov")
7260    (set (attr "prefix")
7261      (if_then_else (eq_attr "alternative" "3")
7262        (const_string "orig")
7263        (const_string "vex")))
7264    (set_attr "mode" "TI,TI,TI,TI,TI,V2SF")])
7265
7266 (define_insn "*vec_concatv2di_rex64_sse4_1"
7267   [(set (match_operand:V2DI 0 "register_operand"     "=x ,x ,Yi,!x,x,x,x")
7268         (vec_concat:V2DI
7269           (match_operand:DI 1 "nonimmediate_operand" " 0 ,mx,r ,*y,0,0,0")
7270           (match_operand:DI 2 "vector_move_operand"  " rm,C ,C ,C ,x,x,m")))]
7271   "TARGET_64BIT && TARGET_SSE4_1"
7272   "@
7273    pinsrq\t{$0x1, %2, %0|%0, %2, 0x1}
7274    movq\t{%1, %0|%0, %1}
7275    movq\t{%1, %0|%0, %1}
7276    movq2dq\t{%1, %0|%0, %1}
7277    punpcklqdq\t{%2, %0|%0, %2}
7278    movlhps\t{%2, %0|%0, %2}
7279    movhps\t{%2, %0|%0, %2}"
7280   [(set_attr "type" "sselog,ssemov,ssemov,ssemov,sselog,ssemov,ssemov")
7281    (set_attr "prefix_extra" "1,*,*,*,*,*,*")
7282    (set_attr "mode" "TI,TI,TI,TI,TI,V4SF,V2SF")])
7283
7284 (define_insn "*vec_concatv2di_rex64_sse"
7285   [(set (match_operand:V2DI 0 "register_operand"     "=Y2 ,Yi,!Y2,Y2,x,x")
7286         (vec_concat:V2DI
7287           (match_operand:DI 1 "nonimmediate_operand" " mY2,r ,*y ,0 ,0,0")
7288           (match_operand:DI 2 "vector_move_operand"  " C  ,C ,C  ,Y2,x,m")))]
7289   "TARGET_64BIT && TARGET_SSE"
7290   "@
7291    movq\t{%1, %0|%0, %1}
7292    movq\t{%1, %0|%0, %1}
7293    movq2dq\t{%1, %0|%0, %1}
7294    punpcklqdq\t{%2, %0|%0, %2}
7295    movlhps\t{%2, %0|%0, %2}
7296    movhps\t{%2, %0|%0, %2}"
7297   [(set_attr "type" "ssemov,ssemov,ssemov,sselog,ssemov,ssemov")
7298    (set_attr "mode" "TI,TI,TI,TI,V4SF,V2SF")])
7299
7300 (define_expand "vec_unpacku_hi_v16qi"
7301   [(match_operand:V8HI 0 "register_operand" "")
7302    (match_operand:V16QI 1 "register_operand" "")]
7303   "TARGET_SSE2"
7304 {
7305   if (TARGET_SSE4_1)
7306     ix86_expand_sse4_unpack (operands, true, true);
7307   else if (TARGET_SSE5)
7308     ix86_expand_sse5_unpack (operands, true, true);
7309   else
7310     ix86_expand_sse_unpack (operands, true, true);
7311   DONE;
7312 })
7313
7314 (define_expand "vec_unpacks_hi_v16qi"
7315   [(match_operand:V8HI 0 "register_operand" "")
7316    (match_operand:V16QI 1 "register_operand" "")]
7317   "TARGET_SSE2"
7318 {
7319   if (TARGET_SSE4_1)
7320     ix86_expand_sse4_unpack (operands, false, true);
7321   else if (TARGET_SSE5)
7322     ix86_expand_sse5_unpack (operands, false, true);
7323   else
7324     ix86_expand_sse_unpack (operands, false, true);
7325   DONE;
7326 })
7327
7328 (define_expand "vec_unpacku_lo_v16qi"
7329   [(match_operand:V8HI 0 "register_operand" "")
7330    (match_operand:V16QI 1 "register_operand" "")]
7331   "TARGET_SSE2"
7332 {
7333   if (TARGET_SSE4_1)
7334     ix86_expand_sse4_unpack (operands, true, false);
7335   else if (TARGET_SSE5)
7336     ix86_expand_sse5_unpack (operands, true, false);
7337   else
7338     ix86_expand_sse_unpack (operands, true, false);
7339   DONE;
7340 })
7341
7342 (define_expand "vec_unpacks_lo_v16qi"
7343   [(match_operand:V8HI 0 "register_operand" "")
7344    (match_operand:V16QI 1 "register_operand" "")]
7345   "TARGET_SSE2"
7346 {
7347   if (TARGET_SSE4_1)
7348     ix86_expand_sse4_unpack (operands, false, false);
7349   else if (TARGET_SSE5)
7350     ix86_expand_sse5_unpack (operands, false, false);
7351   else
7352     ix86_expand_sse_unpack (operands, false, false);
7353   DONE;
7354 })
7355
7356 (define_expand "vec_unpacku_hi_v8hi"
7357   [(match_operand:V4SI 0 "register_operand" "")
7358    (match_operand:V8HI 1 "register_operand" "")]
7359   "TARGET_SSE2"
7360 {
7361   if (TARGET_SSE4_1)
7362     ix86_expand_sse4_unpack (operands, true, true);
7363   else if (TARGET_SSE5)
7364     ix86_expand_sse5_unpack (operands, true, true);
7365   else
7366     ix86_expand_sse_unpack (operands, true, true);
7367   DONE;
7368 })
7369
7370 (define_expand "vec_unpacks_hi_v8hi"
7371   [(match_operand:V4SI 0 "register_operand" "")
7372    (match_operand:V8HI 1 "register_operand" "")]
7373   "TARGET_SSE2"
7374 {
7375   if (TARGET_SSE4_1)
7376     ix86_expand_sse4_unpack (operands, false, true);
7377   else if (TARGET_SSE5)
7378     ix86_expand_sse5_unpack (operands, false, true);
7379   else
7380     ix86_expand_sse_unpack (operands, false, true);
7381   DONE;
7382 })
7383
7384 (define_expand "vec_unpacku_lo_v8hi"
7385   [(match_operand:V4SI 0 "register_operand" "")
7386    (match_operand:V8HI 1 "register_operand" "")]
7387   "TARGET_SSE2"
7388 {
7389   if (TARGET_SSE4_1)
7390     ix86_expand_sse4_unpack (operands, true, false);
7391   else if (TARGET_SSE5)
7392     ix86_expand_sse5_unpack (operands, true, false);
7393   else
7394     ix86_expand_sse_unpack (operands, true, false);
7395   DONE;
7396 })
7397
7398 (define_expand "vec_unpacks_lo_v8hi"
7399   [(match_operand:V4SI 0 "register_operand" "")
7400    (match_operand:V8HI 1 "register_operand" "")]
7401   "TARGET_SSE2"
7402 {
7403   if (TARGET_SSE4_1)
7404     ix86_expand_sse4_unpack (operands, false, false);
7405   else if (TARGET_SSE5)
7406     ix86_expand_sse5_unpack (operands, false, false);
7407   else
7408     ix86_expand_sse_unpack (operands, false, false);
7409   DONE;
7410 })
7411
7412 (define_expand "vec_unpacku_hi_v4si"
7413   [(match_operand:V2DI 0 "register_operand" "")
7414    (match_operand:V4SI 1 "register_operand" "")]
7415   "TARGET_SSE2"
7416 {
7417   if (TARGET_SSE4_1)
7418     ix86_expand_sse4_unpack (operands, true, true);
7419   else if (TARGET_SSE5)
7420     ix86_expand_sse5_unpack (operands, true, true);
7421   else
7422     ix86_expand_sse_unpack (operands, true, true);
7423   DONE;
7424 })
7425
7426 (define_expand "vec_unpacks_hi_v4si"
7427   [(match_operand:V2DI 0 "register_operand" "")
7428    (match_operand:V4SI 1 "register_operand" "")]
7429   "TARGET_SSE2"
7430 {
7431   if (TARGET_SSE4_1)
7432     ix86_expand_sse4_unpack (operands, false, true);
7433   else if (TARGET_SSE5)
7434     ix86_expand_sse5_unpack (operands, false, true);
7435   else
7436     ix86_expand_sse_unpack (operands, false, true);
7437   DONE;
7438 })
7439
7440 (define_expand "vec_unpacku_lo_v4si"
7441   [(match_operand:V2DI 0 "register_operand" "")
7442    (match_operand:V4SI 1 "register_operand" "")]
7443   "TARGET_SSE2"
7444 {
7445   if (TARGET_SSE4_1)
7446     ix86_expand_sse4_unpack (operands, true, false);
7447   else if (TARGET_SSE5)
7448     ix86_expand_sse5_unpack (operands, true, false);
7449   else
7450     ix86_expand_sse_unpack (operands, true, false);
7451   DONE;
7452 })
7453
7454 (define_expand "vec_unpacks_lo_v4si"
7455   [(match_operand:V2DI 0 "register_operand" "")
7456    (match_operand:V4SI 1 "register_operand" "")]
7457   "TARGET_SSE2"
7458 {
7459   if (TARGET_SSE4_1)
7460     ix86_expand_sse4_unpack (operands, false, false);
7461   else if (TARGET_SSE5)
7462     ix86_expand_sse5_unpack (operands, false, false);
7463   else
7464     ix86_expand_sse_unpack (operands, false, false);
7465   DONE;
7466 })
7467
7468 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7469 ;;
7470 ;; Miscellaneous
7471 ;;
7472 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7473
7474 (define_expand "sse2_uavgv16qi3"
7475   [(set (match_operand:V16QI 0 "register_operand" "")
7476         (truncate:V16QI
7477           (lshiftrt:V16HI
7478             (plus:V16HI
7479               (plus:V16HI
7480                 (zero_extend:V16HI
7481                   (match_operand:V16QI 1 "nonimmediate_operand" ""))
7482                 (zero_extend:V16HI
7483                   (match_operand:V16QI 2 "nonimmediate_operand" "")))
7484               (const_vector:V16QI [(const_int 1) (const_int 1)
7485                                    (const_int 1) (const_int 1)
7486                                    (const_int 1) (const_int 1)
7487                                    (const_int 1) (const_int 1)
7488                                    (const_int 1) (const_int 1)
7489                                    (const_int 1) (const_int 1)
7490                                    (const_int 1) (const_int 1)
7491                                    (const_int 1) (const_int 1)]))
7492             (const_int 1))))]
7493   "TARGET_SSE2"
7494   "ix86_fixup_binary_operands_no_copy (PLUS, V16QImode, operands);")
7495
7496 (define_insn "*avx_uavgv16qi3"
7497   [(set (match_operand:V16QI 0 "register_operand" "=x")
7498         (truncate:V16QI
7499           (lshiftrt:V16HI
7500             (plus:V16HI
7501               (plus:V16HI
7502                 (zero_extend:V16HI
7503                   (match_operand:V16QI 1 "nonimmediate_operand" "%x"))
7504                 (zero_extend:V16HI
7505                   (match_operand:V16QI 2 "nonimmediate_operand" "xm")))
7506               (const_vector:V16QI [(const_int 1) (const_int 1)
7507                                    (const_int 1) (const_int 1)
7508                                    (const_int 1) (const_int 1)
7509                                    (const_int 1) (const_int 1)
7510                                    (const_int 1) (const_int 1)
7511                                    (const_int 1) (const_int 1)
7512                                    (const_int 1) (const_int 1)
7513                                    (const_int 1) (const_int 1)]))
7514             (const_int 1))))]
7515   "TARGET_AVX && ix86_binary_operator_ok (PLUS, V16QImode, operands)"
7516   "vpavgb\t{%2, %1, %0|%0, %1, %2}"
7517   [(set_attr "type" "sseiadd")
7518    (set_attr "prefix" "vex")
7519    (set_attr "mode" "TI")])
7520
7521 (define_insn "*sse2_uavgv16qi3"
7522   [(set (match_operand:V16QI 0 "register_operand" "=x")
7523         (truncate:V16QI
7524           (lshiftrt:V16HI
7525             (plus:V16HI
7526               (plus:V16HI
7527                 (zero_extend:V16HI
7528                   (match_operand:V16QI 1 "nonimmediate_operand" "%0"))
7529                 (zero_extend:V16HI
7530                   (match_operand:V16QI 2 "nonimmediate_operand" "xm")))
7531               (const_vector:V16QI [(const_int 1) (const_int 1)
7532                                    (const_int 1) (const_int 1)
7533                                    (const_int 1) (const_int 1)
7534                                    (const_int 1) (const_int 1)
7535                                    (const_int 1) (const_int 1)
7536                                    (const_int 1) (const_int 1)
7537                                    (const_int 1) (const_int 1)
7538                                    (const_int 1) (const_int 1)]))
7539             (const_int 1))))]
7540   "TARGET_SSE2 && ix86_binary_operator_ok (PLUS, V16QImode, operands)"
7541   "pavgb\t{%2, %0|%0, %2}"
7542   [(set_attr "type" "sseiadd")
7543    (set_attr "prefix_data16" "1")
7544    (set_attr "mode" "TI")])
7545
7546 (define_expand "sse2_uavgv8hi3"
7547   [(set (match_operand:V8HI 0 "register_operand" "")
7548         (truncate:V8HI
7549           (lshiftrt:V8SI
7550             (plus:V8SI
7551               (plus:V8SI
7552                 (zero_extend:V8SI
7553                   (match_operand:V8HI 1 "nonimmediate_operand" ""))
7554                 (zero_extend:V8SI
7555                   (match_operand:V8HI 2 "nonimmediate_operand" "")))
7556               (const_vector:V8HI [(const_int 1) (const_int 1)
7557                                   (const_int 1) (const_int 1)
7558                                   (const_int 1) (const_int 1)
7559                                   (const_int 1) (const_int 1)]))
7560             (const_int 1))))]
7561   "TARGET_SSE2"
7562   "ix86_fixup_binary_operands_no_copy (PLUS, V8HImode, operands);")
7563
7564 (define_insn "*avx_uavgv8hi3"
7565   [(set (match_operand:V8HI 0 "register_operand" "=x")
7566         (truncate:V8HI
7567           (lshiftrt:V8SI
7568             (plus:V8SI
7569               (plus:V8SI
7570                 (zero_extend:V8SI
7571                   (match_operand:V8HI 1 "nonimmediate_operand" "%x"))
7572                 (zero_extend:V8SI
7573                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
7574               (const_vector:V8HI [(const_int 1) (const_int 1)
7575                                   (const_int 1) (const_int 1)
7576                                   (const_int 1) (const_int 1)
7577                                   (const_int 1) (const_int 1)]))
7578             (const_int 1))))]
7579   "TARGET_AVX && ix86_binary_operator_ok (PLUS, V8HImode, operands)"
7580   "vpavgw\t{%2, %1, %0|%0, %1, %2}"
7581   [(set_attr "type" "sseiadd")
7582    (set_attr "prefix" "vex")
7583    (set_attr "mode" "TI")])
7584
7585 (define_insn "*sse2_uavgv8hi3"
7586   [(set (match_operand:V8HI 0 "register_operand" "=x")
7587         (truncate:V8HI
7588           (lshiftrt:V8SI
7589             (plus:V8SI
7590               (plus:V8SI
7591                 (zero_extend:V8SI
7592                   (match_operand:V8HI 1 "nonimmediate_operand" "%0"))
7593                 (zero_extend:V8SI
7594                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
7595               (const_vector:V8HI [(const_int 1) (const_int 1)
7596                                   (const_int 1) (const_int 1)
7597                                   (const_int 1) (const_int 1)
7598                                   (const_int 1) (const_int 1)]))
7599             (const_int 1))))]
7600   "TARGET_SSE2 && ix86_binary_operator_ok (PLUS, V8HImode, operands)"
7601   "pavgw\t{%2, %0|%0, %2}"
7602   [(set_attr "type" "sseiadd")
7603    (set_attr "prefix_data16" "1")
7604    (set_attr "mode" "TI")])
7605
7606 ;; The correct representation for this is absolutely enormous, and
7607 ;; surely not generally useful.
7608 (define_insn "*avx_psadbw"
7609   [(set (match_operand:V2DI 0 "register_operand" "=x")
7610         (unspec:V2DI [(match_operand:V16QI 1 "register_operand" "x")
7611                       (match_operand:V16QI 2 "nonimmediate_operand" "xm")]
7612                      UNSPEC_PSADBW))]
7613   "TARGET_AVX"
7614   "vpsadbw\t{%2, %1, %0|%0, %1, %2}"
7615   [(set_attr "type" "sseiadd")
7616    (set_attr "prefix" "vex")
7617    (set_attr "mode" "TI")])
7618
7619 (define_insn "sse2_psadbw"
7620   [(set (match_operand:V2DI 0 "register_operand" "=x")
7621         (unspec:V2DI [(match_operand:V16QI 1 "register_operand" "0")
7622                       (match_operand:V16QI 2 "nonimmediate_operand" "xm")]
7623                      UNSPEC_PSADBW))]
7624   "TARGET_SSE2"
7625   "psadbw\t{%2, %0|%0, %2}"
7626   [(set_attr "type" "sseiadd")
7627    (set_attr "prefix_data16" "1")
7628    (set_attr "mode" "TI")])
7629
7630 (define_insn "avx_movmskp<avxmodesuffixf2c>256"
7631   [(set (match_operand:SI 0 "register_operand" "=r")
7632         (unspec:SI
7633           [(match_operand:AVX256MODEF2P 1 "register_operand" "x")]
7634           UNSPEC_MOVMSK))]
7635   "AVX256_VEC_FLOAT_MODE_P (<MODE>mode)"
7636   "vmovmskp<avxmodesuffixf2c>\t{%1, %0|%0, %1}"
7637   [(set_attr "type" "ssecvt")
7638    (set_attr "prefix" "vex")
7639    (set_attr "mode" "<MODE>")])
7640
7641 (define_insn "<sse>_movmskp<ssemodesuffixf2c>"
7642   [(set (match_operand:SI 0 "register_operand" "=r")
7643         (unspec:SI
7644           [(match_operand:SSEMODEF2P 1 "register_operand" "x")]
7645           UNSPEC_MOVMSK))]
7646   "SSE_VEC_FLOAT_MODE_P (<MODE>mode)"
7647   "%vmovmskp<ssemodesuffixf2c>\t{%1, %0|%0, %1}"
7648   [(set_attr "type" "ssecvt")
7649    (set_attr "prefix" "maybe_vex")
7650    (set_attr "mode" "<MODE>")])
7651
7652 (define_insn "sse2_pmovmskb"
7653   [(set (match_operand:SI 0 "register_operand" "=r")
7654         (unspec:SI [(match_operand:V16QI 1 "register_operand" "x")]
7655                    UNSPEC_MOVMSK))]
7656   "TARGET_SSE2"
7657   "%vpmovmskb\t{%1, %0|%0, %1}"
7658   [(set_attr "type" "ssecvt")
7659    (set_attr "prefix_data16" "1")
7660    (set_attr "prefix" "maybe_vex")
7661    (set_attr "mode" "SI")])
7662
7663 (define_expand "sse2_maskmovdqu"
7664   [(set (match_operand:V16QI 0 "memory_operand" "")
7665         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "")
7666                        (match_operand:V16QI 2 "register_operand" "")
7667                        (match_dup 0)]
7668                       UNSPEC_MASKMOV))]
7669   "TARGET_SSE2"
7670   "")
7671
7672 (define_insn "*sse2_maskmovdqu"
7673   [(set (mem:V16QI (match_operand:SI 0 "register_operand" "D"))
7674         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
7675                        (match_operand:V16QI 2 "register_operand" "x")
7676                        (mem:V16QI (match_dup 0))]
7677                       UNSPEC_MASKMOV))]
7678   "TARGET_SSE2 && !TARGET_64BIT"
7679   ;; @@@ check ordering of operands in intel/nonintel syntax
7680   "%vmaskmovdqu\t{%2, %1|%1, %2}"
7681   [(set_attr "type" "ssecvt")
7682    (set_attr "prefix_data16" "1")
7683    (set_attr "prefix" "maybe_vex")
7684    (set_attr "mode" "TI")])
7685
7686 (define_insn "*sse2_maskmovdqu_rex64"
7687   [(set (mem:V16QI (match_operand:DI 0 "register_operand" "D"))
7688         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
7689                        (match_operand:V16QI 2 "register_operand" "x")
7690                        (mem:V16QI (match_dup 0))]
7691                       UNSPEC_MASKMOV))]
7692   "TARGET_SSE2 && TARGET_64BIT"
7693   ;; @@@ check ordering of operands in intel/nonintel syntax
7694   "%vmaskmovdqu\t{%2, %1|%1, %2}"
7695   [(set_attr "type" "ssecvt")
7696    (set_attr "prefix_data16" "1")
7697    (set_attr "prefix" "maybe_vex")
7698    (set_attr "mode" "TI")])
7699
7700 (define_insn "sse_ldmxcsr"
7701   [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")]
7702                     UNSPECV_LDMXCSR)]
7703   "TARGET_SSE"
7704   "%vldmxcsr\t%0"
7705   [(set_attr "type" "sse")
7706    (set_attr "prefix" "maybe_vex")
7707    (set_attr "memory" "load")])
7708
7709 (define_insn "sse_stmxcsr"
7710   [(set (match_operand:SI 0 "memory_operand" "=m")
7711         (unspec_volatile:SI [(const_int 0)] UNSPECV_STMXCSR))]
7712   "TARGET_SSE"
7713   "%vstmxcsr\t%0"
7714   [(set_attr "type" "sse")
7715    (set_attr "prefix" "maybe_vex")
7716    (set_attr "memory" "store")])
7717
7718 (define_expand "sse_sfence"
7719   [(set (match_dup 0)
7720         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
7721   "TARGET_SSE || TARGET_3DNOW_A"
7722 {
7723   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
7724   MEM_VOLATILE_P (operands[0]) = 1;
7725 })
7726
7727 (define_insn "*sse_sfence"
7728   [(set (match_operand:BLK 0 "" "")
7729         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
7730   "TARGET_SSE || TARGET_3DNOW_A"
7731   "sfence"
7732   [(set_attr "type" "sse")
7733    (set_attr "memory" "unknown")])
7734
7735 (define_insn "sse2_clflush"
7736   [(unspec_volatile [(match_operand 0 "address_operand" "p")]
7737                     UNSPECV_CLFLUSH)]
7738   "TARGET_SSE2"
7739   "clflush\t%a0"
7740   [(set_attr "type" "sse")
7741    (set_attr "memory" "unknown")])
7742
7743 (define_expand "sse2_mfence"
7744   [(set (match_dup 0)
7745         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
7746   "TARGET_SSE2"
7747 {
7748   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
7749   MEM_VOLATILE_P (operands[0]) = 1;
7750 })
7751
7752 (define_insn "*sse2_mfence"
7753   [(set (match_operand:BLK 0 "" "")
7754         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
7755   "TARGET_64BIT || TARGET_SSE2"
7756   "mfence"
7757   [(set_attr "type" "sse")
7758    (set_attr "memory" "unknown")])
7759
7760 (define_expand "sse2_lfence"
7761   [(set (match_dup 0)
7762         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
7763   "TARGET_SSE2"
7764 {
7765   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
7766   MEM_VOLATILE_P (operands[0]) = 1;
7767 })
7768
7769 (define_insn "*sse2_lfence"
7770   [(set (match_operand:BLK 0 "" "")
7771         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
7772   "TARGET_SSE2"
7773   "lfence"
7774   [(set_attr "type" "sse")
7775    (set_attr "memory" "unknown")])
7776
7777 (define_insn "sse3_mwait"
7778   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
7779                      (match_operand:SI 1 "register_operand" "c")]
7780                     UNSPECV_MWAIT)]
7781   "TARGET_SSE3"
7782 ;; 64bit version is "mwait %rax,%rcx". But only lower 32bits are used.
7783 ;; Since 32bit register operands are implicitly zero extended to 64bit,
7784 ;; we only need to set up 32bit registers.
7785   "mwait"
7786   [(set_attr "length" "3")])
7787
7788 (define_insn "sse3_monitor"
7789   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
7790                      (match_operand:SI 1 "register_operand" "c")
7791                      (match_operand:SI 2 "register_operand" "d")]
7792                     UNSPECV_MONITOR)]
7793   "TARGET_SSE3 && !TARGET_64BIT"
7794   "monitor\t%0, %1, %2"
7795   [(set_attr "length" "3")])
7796
7797 (define_insn "sse3_monitor64"
7798   [(unspec_volatile [(match_operand:DI 0 "register_operand" "a")
7799                      (match_operand:SI 1 "register_operand" "c")
7800                      (match_operand:SI 2 "register_operand" "d")]
7801                     UNSPECV_MONITOR)]
7802   "TARGET_SSE3 && TARGET_64BIT"
7803 ;; 64bit version is "monitor %rax,%rcx,%rdx". But only lower 32bits in
7804 ;; RCX and RDX are used.  Since 32bit register operands are implicitly
7805 ;; zero extended to 64bit, we only need to set up 32bit registers.
7806   "monitor"
7807   [(set_attr "length" "3")])
7808
7809 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7810 ;;
7811 ;; SSSE3 instructions
7812 ;;
7813 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7814
7815 (define_insn "*avx_phaddwv8hi3"
7816   [(set (match_operand:V8HI 0 "register_operand" "=x")
7817         (vec_concat:V8HI
7818           (vec_concat:V4HI
7819             (vec_concat:V2HI
7820               (plus:HI
7821                 (vec_select:HI
7822                   (match_operand:V8HI 1 "register_operand" "x")
7823                   (parallel [(const_int 0)]))
7824                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
7825               (plus:HI
7826                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
7827                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
7828             (vec_concat:V2HI
7829               (plus:HI
7830                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
7831                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
7832               (plus:HI
7833                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
7834                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
7835           (vec_concat:V4HI
7836             (vec_concat:V2HI
7837               (plus:HI
7838                 (vec_select:HI
7839                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
7840                   (parallel [(const_int 0)]))
7841                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
7842               (plus:HI
7843                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
7844                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
7845             (vec_concat:V2HI
7846               (plus:HI
7847                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
7848                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
7849               (plus:HI
7850                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
7851                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
7852   "TARGET_AVX"
7853   "vphaddw\t{%2, %1, %0|%0, %1, %2}"
7854   [(set_attr "type" "sseiadd")
7855    (set_attr "prefix" "vex")
7856    (set_attr "mode" "TI")])
7857
7858 (define_insn "ssse3_phaddwv8hi3"
7859   [(set (match_operand:V8HI 0 "register_operand" "=x")
7860         (vec_concat:V8HI
7861           (vec_concat:V4HI
7862             (vec_concat:V2HI
7863               (plus:HI
7864                 (vec_select:HI
7865                   (match_operand:V8HI 1 "register_operand" "0")
7866                   (parallel [(const_int 0)]))
7867                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
7868               (plus:HI
7869                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
7870                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
7871             (vec_concat:V2HI
7872               (plus:HI
7873                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
7874                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
7875               (plus:HI
7876                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
7877                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
7878           (vec_concat:V4HI
7879             (vec_concat:V2HI
7880               (plus:HI
7881                 (vec_select:HI
7882                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
7883                   (parallel [(const_int 0)]))
7884                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
7885               (plus:HI
7886                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
7887                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
7888             (vec_concat:V2HI
7889               (plus:HI
7890                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
7891                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
7892               (plus:HI
7893                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
7894                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
7895   "TARGET_SSSE3"
7896   "phaddw\t{%2, %0|%0, %2}"
7897   [(set_attr "type" "sseiadd")
7898    (set_attr "prefix_data16" "1")
7899    (set_attr "prefix_extra" "1")
7900    (set_attr "mode" "TI")])
7901
7902 (define_insn "ssse3_phaddwv4hi3"
7903   [(set (match_operand:V4HI 0 "register_operand" "=y")
7904         (vec_concat:V4HI
7905           (vec_concat:V2HI
7906             (plus:HI
7907               (vec_select:HI
7908                 (match_operand:V4HI 1 "register_operand" "0")
7909                 (parallel [(const_int 0)]))
7910               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
7911             (plus:HI
7912               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
7913               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
7914           (vec_concat:V2HI
7915             (plus:HI
7916               (vec_select:HI
7917                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
7918                 (parallel [(const_int 0)]))
7919               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
7920             (plus:HI
7921               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
7922               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
7923   "TARGET_SSSE3"
7924   "phaddw\t{%2, %0|%0, %2}"
7925   [(set_attr "type" "sseiadd")
7926    (set_attr "prefix_extra" "1")
7927    (set_attr "mode" "DI")])
7928
7929 (define_insn "*avx_phadddv4si3"
7930   [(set (match_operand:V4SI 0 "register_operand" "=x")
7931         (vec_concat:V4SI
7932           (vec_concat:V2SI
7933             (plus:SI
7934               (vec_select:SI
7935                 (match_operand:V4SI 1 "register_operand" "x")
7936                 (parallel [(const_int 0)]))
7937               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
7938             (plus:SI
7939               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
7940               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
7941           (vec_concat:V2SI
7942             (plus:SI
7943               (vec_select:SI
7944                 (match_operand:V4SI 2 "nonimmediate_operand" "xm")
7945                 (parallel [(const_int 0)]))
7946               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
7947             (plus:SI
7948               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
7949               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
7950   "TARGET_AVX"
7951   "vphaddd\t{%2, %1, %0|%0, %1, %2}"
7952   [(set_attr "type" "sseiadd")
7953    (set_attr "prefix" "vex")
7954    (set_attr "mode" "TI")])
7955
7956 (define_insn "ssse3_phadddv4si3"
7957   [(set (match_operand:V4SI 0 "register_operand" "=x")
7958         (vec_concat:V4SI
7959           (vec_concat:V2SI
7960             (plus:SI
7961               (vec_select:SI
7962                 (match_operand:V4SI 1 "register_operand" "0")
7963                 (parallel [(const_int 0)]))
7964               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
7965             (plus:SI
7966               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
7967               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
7968           (vec_concat:V2SI
7969             (plus:SI
7970               (vec_select:SI
7971                 (match_operand:V4SI 2 "nonimmediate_operand" "xm")
7972                 (parallel [(const_int 0)]))
7973               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
7974             (plus:SI
7975               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
7976               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
7977   "TARGET_SSSE3"
7978   "phaddd\t{%2, %0|%0, %2}"
7979   [(set_attr "type" "sseiadd")
7980    (set_attr "prefix_data16" "1")
7981    (set_attr "prefix_extra" "1")
7982    (set_attr "mode" "TI")])
7983
7984 (define_insn "ssse3_phadddv2si3"
7985   [(set (match_operand:V2SI 0 "register_operand" "=y")
7986         (vec_concat:V2SI
7987           (plus:SI
7988             (vec_select:SI
7989               (match_operand:V2SI 1 "register_operand" "0")
7990               (parallel [(const_int 0)]))
7991             (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
7992           (plus:SI
7993             (vec_select:SI
7994               (match_operand:V2SI 2 "nonimmediate_operand" "ym")
7995               (parallel [(const_int 0)]))
7996             (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))))]
7997   "TARGET_SSSE3"
7998   "phaddd\t{%2, %0|%0, %2}"
7999   [(set_attr "type" "sseiadd")
8000    (set_attr "prefix_extra" "1")
8001    (set_attr "mode" "DI")])
8002
8003 (define_insn "*avx_phaddswv8hi3"
8004   [(set (match_operand:V8HI 0 "register_operand" "=x")
8005         (vec_concat:V8HI
8006           (vec_concat:V4HI
8007             (vec_concat:V2HI
8008               (ss_plus:HI
8009                 (vec_select:HI
8010                   (match_operand:V8HI 1 "register_operand" "x")
8011                   (parallel [(const_int 0)]))
8012                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8013               (ss_plus:HI
8014                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8015                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8016             (vec_concat:V2HI
8017               (ss_plus:HI
8018                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8019                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8020               (ss_plus:HI
8021                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8022                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8023           (vec_concat:V4HI
8024             (vec_concat:V2HI
8025               (ss_plus:HI
8026                 (vec_select:HI
8027                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8028                   (parallel [(const_int 0)]))
8029                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8030               (ss_plus:HI
8031                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8032                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8033             (vec_concat:V2HI
8034               (ss_plus:HI
8035                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8036                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8037               (ss_plus:HI
8038                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8039                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8040   "TARGET_AVX"
8041   "vphaddsw\t{%2, %1, %0|%0, %1, %2}"
8042   [(set_attr "type" "sseiadd")
8043    (set_attr "prefix" "vex")
8044    (set_attr "mode" "TI")])
8045
8046 (define_insn "ssse3_phaddswv8hi3"
8047   [(set (match_operand:V8HI 0 "register_operand" "=x")
8048         (vec_concat:V8HI
8049           (vec_concat:V4HI
8050             (vec_concat:V2HI
8051               (ss_plus:HI
8052                 (vec_select:HI
8053                   (match_operand:V8HI 1 "register_operand" "0")
8054                   (parallel [(const_int 0)]))
8055                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8056               (ss_plus:HI
8057                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8058                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8059             (vec_concat:V2HI
8060               (ss_plus:HI
8061                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8062                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8063               (ss_plus:HI
8064                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8065                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8066           (vec_concat:V4HI
8067             (vec_concat:V2HI
8068               (ss_plus:HI
8069                 (vec_select:HI
8070                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8071                   (parallel [(const_int 0)]))
8072                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8073               (ss_plus:HI
8074                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8075                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8076             (vec_concat:V2HI
8077               (ss_plus:HI
8078                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8079                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8080               (ss_plus:HI
8081                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8082                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8083   "TARGET_SSSE3"
8084   "phaddsw\t{%2, %0|%0, %2}"
8085   [(set_attr "type" "sseiadd")
8086    (set_attr "prefix_data16" "1")
8087    (set_attr "prefix_extra" "1")
8088    (set_attr "mode" "TI")])
8089
8090 (define_insn "ssse3_phaddswv4hi3"
8091   [(set (match_operand:V4HI 0 "register_operand" "=y")
8092         (vec_concat:V4HI
8093           (vec_concat:V2HI
8094             (ss_plus:HI
8095               (vec_select:HI
8096                 (match_operand:V4HI 1 "register_operand" "0")
8097                 (parallel [(const_int 0)]))
8098               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8099             (ss_plus:HI
8100               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8101               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8102           (vec_concat:V2HI
8103             (ss_plus:HI
8104               (vec_select:HI
8105                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8106                 (parallel [(const_int 0)]))
8107               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8108             (ss_plus:HI
8109               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8110               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8111   "TARGET_SSSE3"
8112   "phaddsw\t{%2, %0|%0, %2}"
8113   [(set_attr "type" "sseiadd")
8114    (set_attr "prefix_extra" "1")
8115    (set_attr "mode" "DI")])
8116
8117 (define_insn "*avx_phsubwv8hi3"
8118   [(set (match_operand:V8HI 0 "register_operand" "=x")
8119         (vec_concat:V8HI
8120           (vec_concat:V4HI
8121             (vec_concat:V2HI
8122               (minus:HI
8123                 (vec_select:HI
8124                   (match_operand:V8HI 1 "register_operand" "x")
8125                   (parallel [(const_int 0)]))
8126                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8127               (minus:HI
8128                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8129                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8130             (vec_concat:V2HI
8131               (minus:HI
8132                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8133                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8134               (minus:HI
8135                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8136                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8137           (vec_concat:V4HI
8138             (vec_concat:V2HI
8139               (minus:HI
8140                 (vec_select:HI
8141                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8142                   (parallel [(const_int 0)]))
8143                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8144               (minus:HI
8145                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8146                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8147             (vec_concat:V2HI
8148               (minus:HI
8149                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8150                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8151               (minus:HI
8152                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8153                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8154   "TARGET_AVX"
8155   "vphsubw\t{%2, %1, %0|%0, %1, %2}"
8156   [(set_attr "type" "sseiadd")
8157    (set_attr "prefix" "vex")
8158    (set_attr "mode" "TI")])
8159
8160 (define_insn "ssse3_phsubwv8hi3"
8161   [(set (match_operand:V8HI 0 "register_operand" "=x")
8162         (vec_concat:V8HI
8163           (vec_concat:V4HI
8164             (vec_concat:V2HI
8165               (minus:HI
8166                 (vec_select:HI
8167                   (match_operand:V8HI 1 "register_operand" "0")
8168                   (parallel [(const_int 0)]))
8169                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8170               (minus:HI
8171                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8172                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8173             (vec_concat:V2HI
8174               (minus:HI
8175                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8176                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8177               (minus:HI
8178                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8179                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8180           (vec_concat:V4HI
8181             (vec_concat:V2HI
8182               (minus:HI
8183                 (vec_select:HI
8184                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8185                   (parallel [(const_int 0)]))
8186                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8187               (minus:HI
8188                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8189                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8190             (vec_concat:V2HI
8191               (minus:HI
8192                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8193                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8194               (minus:HI
8195                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8196                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8197   "TARGET_SSSE3"
8198   "phsubw\t{%2, %0|%0, %2}"
8199   [(set_attr "type" "sseiadd")
8200    (set_attr "prefix_data16" "1")
8201    (set_attr "prefix_extra" "1")
8202    (set_attr "mode" "TI")])
8203
8204 (define_insn "ssse3_phsubwv4hi3"
8205   [(set (match_operand:V4HI 0 "register_operand" "=y")
8206         (vec_concat:V4HI
8207           (vec_concat:V2HI
8208             (minus:HI
8209               (vec_select:HI
8210                 (match_operand:V4HI 1 "register_operand" "0")
8211                 (parallel [(const_int 0)]))
8212               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8213             (minus:HI
8214               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8215               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8216           (vec_concat:V2HI
8217             (minus:HI
8218               (vec_select:HI
8219                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8220                 (parallel [(const_int 0)]))
8221               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8222             (minus:HI
8223               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8224               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8225   "TARGET_SSSE3"
8226   "phsubw\t{%2, %0|%0, %2}"
8227   [(set_attr "type" "sseiadd")
8228    (set_attr "prefix_extra" "1")
8229    (set_attr "mode" "DI")])
8230
8231 (define_insn "*avx_phsubdv4si3"
8232   [(set (match_operand:V4SI 0 "register_operand" "=x")
8233         (vec_concat:V4SI
8234           (vec_concat:V2SI
8235             (minus:SI
8236               (vec_select:SI
8237                 (match_operand:V4SI 1 "register_operand" "x")
8238                 (parallel [(const_int 0)]))
8239               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8240             (minus:SI
8241               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8242               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8243           (vec_concat:V2SI
8244             (minus:SI
8245               (vec_select:SI
8246                 (match_operand:V4SI 2 "nonimmediate_operand" "xm")
8247                 (parallel [(const_int 0)]))
8248               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8249             (minus:SI
8250               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8251               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
8252   "TARGET_AVX"
8253   "vphsubd\t{%2, %1, %0|%0, %1, %2}"
8254   [(set_attr "type" "sseiadd")
8255    (set_attr "prefix" "vex")
8256    (set_attr "mode" "TI")])
8257
8258 (define_insn "ssse3_phsubdv4si3"
8259   [(set (match_operand:V4SI 0 "register_operand" "=x")
8260         (vec_concat:V4SI
8261           (vec_concat:V2SI
8262             (minus:SI
8263               (vec_select:SI
8264                 (match_operand:V4SI 1 "register_operand" "0")
8265                 (parallel [(const_int 0)]))
8266               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8267             (minus:SI
8268               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8269               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8270           (vec_concat:V2SI
8271             (minus:SI
8272               (vec_select:SI
8273                 (match_operand:V4SI 2 "nonimmediate_operand" "xm")
8274                 (parallel [(const_int 0)]))
8275               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8276             (minus:SI
8277               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8278               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
8279   "TARGET_SSSE3"
8280   "phsubd\t{%2, %0|%0, %2}"
8281   [(set_attr "type" "sseiadd")
8282    (set_attr "prefix_data16" "1")
8283    (set_attr "prefix_extra" "1")
8284    (set_attr "mode" "TI")])
8285
8286 (define_insn "ssse3_phsubdv2si3"
8287   [(set (match_operand:V2SI 0 "register_operand" "=y")
8288         (vec_concat:V2SI
8289           (minus:SI
8290             (vec_select:SI
8291               (match_operand:V2SI 1 "register_operand" "0")
8292               (parallel [(const_int 0)]))
8293             (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8294           (minus:SI
8295             (vec_select:SI
8296               (match_operand:V2SI 2 "nonimmediate_operand" "ym")
8297               (parallel [(const_int 0)]))
8298             (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))))]
8299   "TARGET_SSSE3"
8300   "phsubd\t{%2, %0|%0, %2}"
8301   [(set_attr "type" "sseiadd")
8302    (set_attr "prefix_extra" "1")
8303    (set_attr "mode" "DI")])
8304
8305 (define_insn "*avx_phsubswv8hi3"
8306   [(set (match_operand:V8HI 0 "register_operand" "=x")
8307         (vec_concat:V8HI
8308           (vec_concat:V4HI
8309             (vec_concat:V2HI
8310               (ss_minus:HI
8311                 (vec_select:HI
8312                   (match_operand:V8HI 1 "register_operand" "x")
8313                   (parallel [(const_int 0)]))
8314                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8315               (ss_minus:HI
8316                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8317                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8318             (vec_concat:V2HI
8319               (ss_minus:HI
8320                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8321                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8322               (ss_minus:HI
8323                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8324                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8325           (vec_concat:V4HI
8326             (vec_concat:V2HI
8327               (ss_minus:HI
8328                 (vec_select:HI
8329                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8330                   (parallel [(const_int 0)]))
8331                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8332               (ss_minus:HI
8333                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8334                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8335             (vec_concat:V2HI
8336               (ss_minus:HI
8337                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8338                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8339               (ss_minus:HI
8340                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8341                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8342   "TARGET_AVX"
8343   "vphsubsw\t{%2, %1, %0|%0, %1, %2}"
8344   [(set_attr "type" "sseiadd")
8345    (set_attr "prefix" "vex")
8346    (set_attr "mode" "TI")])
8347
8348 (define_insn "ssse3_phsubswv8hi3"
8349   [(set (match_operand:V8HI 0 "register_operand" "=x")
8350         (vec_concat:V8HI
8351           (vec_concat:V4HI
8352             (vec_concat:V2HI
8353               (ss_minus:HI
8354                 (vec_select:HI
8355                   (match_operand:V8HI 1 "register_operand" "0")
8356                   (parallel [(const_int 0)]))
8357                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8358               (ss_minus:HI
8359                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8360                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8361             (vec_concat:V2HI
8362               (ss_minus:HI
8363                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8364                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8365               (ss_minus:HI
8366                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8367                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8368           (vec_concat:V4HI
8369             (vec_concat:V2HI
8370               (ss_minus:HI
8371                 (vec_select:HI
8372                   (match_operand:V8HI 2 "nonimmediate_operand" "xm")
8373                   (parallel [(const_int 0)]))
8374                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8375               (ss_minus:HI
8376                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8377                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8378             (vec_concat:V2HI
8379               (ss_minus:HI
8380                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8381                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8382               (ss_minus:HI
8383                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8384                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8385   "TARGET_SSSE3"
8386   "phsubsw\t{%2, %0|%0, %2}"
8387   [(set_attr "type" "sseiadd")
8388    (set_attr "prefix_data16" "1")
8389    (set_attr "prefix_extra" "1")
8390    (set_attr "mode" "TI")])
8391
8392 (define_insn "ssse3_phsubswv4hi3"
8393   [(set (match_operand:V4HI 0 "register_operand" "=y")
8394         (vec_concat:V4HI
8395           (vec_concat:V2HI
8396             (ss_minus:HI
8397               (vec_select:HI
8398                 (match_operand:V4HI 1 "register_operand" "0")
8399                 (parallel [(const_int 0)]))
8400               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8401             (ss_minus:HI
8402               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8403               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8404           (vec_concat:V2HI
8405             (ss_minus:HI
8406               (vec_select:HI
8407                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8408                 (parallel [(const_int 0)]))
8409               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8410             (ss_minus:HI
8411               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8412               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8413   "TARGET_SSSE3"
8414   "phsubsw\t{%2, %0|%0, %2}"
8415   [(set_attr "type" "sseiadd")
8416    (set_attr "prefix_extra" "1")
8417    (set_attr "mode" "DI")])
8418
8419 (define_insn "*avx_pmaddubsw128"
8420   [(set (match_operand:V8HI 0 "register_operand" "=x")
8421         (ss_plus:V8HI
8422           (mult:V8HI
8423             (zero_extend:V8HI
8424               (vec_select:V8QI
8425                 (match_operand:V16QI 1 "register_operand" "x")
8426                 (parallel [(const_int 0)
8427                            (const_int 2)
8428                            (const_int 4)
8429                            (const_int 6)
8430                            (const_int 8)
8431                            (const_int 10)
8432                            (const_int 12)
8433                            (const_int 14)])))
8434             (sign_extend:V8HI
8435               (vec_select:V8QI
8436                 (match_operand:V16QI 2 "nonimmediate_operand" "xm")
8437                 (parallel [(const_int 0)
8438                            (const_int 2)
8439                            (const_int 4)
8440                            (const_int 6)
8441                            (const_int 8)
8442                            (const_int 10)
8443                            (const_int 12)
8444                            (const_int 14)]))))
8445           (mult:V8HI
8446             (zero_extend:V8HI
8447               (vec_select:V8QI (match_dup 1)
8448                 (parallel [(const_int 1)
8449                            (const_int 3)
8450                            (const_int 5)
8451                            (const_int 7)
8452                            (const_int 9)
8453                            (const_int 11)
8454                            (const_int 13)
8455                            (const_int 15)])))
8456             (sign_extend:V8HI
8457               (vec_select:V8QI (match_dup 2)
8458                 (parallel [(const_int 1)
8459                            (const_int 3)
8460                            (const_int 5)
8461                            (const_int 7)
8462                            (const_int 9)
8463                            (const_int 11)
8464                            (const_int 13)
8465                            (const_int 15)]))))))]
8466   "TARGET_AVX"
8467   "vpmaddubsw\t{%2, %1, %0|%0, %1, %2}"
8468   [(set_attr "type" "sseiadd")
8469    (set_attr "prefix" "vex")
8470    (set_attr "mode" "TI")])
8471
8472 (define_insn "ssse3_pmaddubsw128"
8473   [(set (match_operand:V8HI 0 "register_operand" "=x")
8474         (ss_plus:V8HI
8475           (mult:V8HI
8476             (zero_extend:V8HI
8477               (vec_select:V8QI
8478                 (match_operand:V16QI 1 "register_operand" "0")
8479                 (parallel [(const_int 0)
8480                            (const_int 2)
8481                            (const_int 4)
8482                            (const_int 6)
8483                            (const_int 8)
8484                            (const_int 10)
8485                            (const_int 12)
8486                            (const_int 14)])))
8487             (sign_extend:V8HI
8488               (vec_select:V8QI
8489                 (match_operand:V16QI 2 "nonimmediate_operand" "xm")
8490                 (parallel [(const_int 0)
8491                            (const_int 2)
8492                            (const_int 4)
8493                            (const_int 6)
8494                            (const_int 8)
8495                            (const_int 10)
8496                            (const_int 12)
8497                            (const_int 14)]))))
8498           (mult:V8HI
8499             (zero_extend:V8HI
8500               (vec_select:V8QI (match_dup 1)
8501                 (parallel [(const_int 1)
8502                            (const_int 3)
8503                            (const_int 5)
8504                            (const_int 7)
8505                            (const_int 9)
8506                            (const_int 11)
8507                            (const_int 13)
8508                            (const_int 15)])))
8509             (sign_extend:V8HI
8510               (vec_select:V8QI (match_dup 2)
8511                 (parallel [(const_int 1)
8512                            (const_int 3)
8513                            (const_int 5)
8514                            (const_int 7)
8515                            (const_int 9)
8516                            (const_int 11)
8517                            (const_int 13)
8518                            (const_int 15)]))))))]
8519   "TARGET_SSSE3"
8520   "pmaddubsw\t{%2, %0|%0, %2}"
8521   [(set_attr "type" "sseiadd")
8522    (set_attr "prefix_data16" "1")
8523    (set_attr "prefix_extra" "1")
8524    (set_attr "mode" "TI")])
8525
8526 (define_insn "ssse3_pmaddubsw"
8527   [(set (match_operand:V4HI 0 "register_operand" "=y")
8528         (ss_plus:V4HI
8529           (mult:V4HI
8530             (zero_extend:V4HI
8531               (vec_select:V4QI
8532                 (match_operand:V8QI 1 "register_operand" "0")
8533                 (parallel [(const_int 0)
8534                            (const_int 2)
8535                            (const_int 4)
8536                            (const_int 6)])))
8537             (sign_extend:V4HI
8538               (vec_select:V4QI
8539                 (match_operand:V8QI 2 "nonimmediate_operand" "ym")
8540                 (parallel [(const_int 0)
8541                            (const_int 2)
8542                            (const_int 4)
8543                            (const_int 6)]))))
8544           (mult:V4HI
8545             (zero_extend:V4HI
8546               (vec_select:V4QI (match_dup 1)
8547                 (parallel [(const_int 1)
8548                            (const_int 3)
8549                            (const_int 5)
8550                            (const_int 7)])))
8551             (sign_extend:V4HI
8552               (vec_select:V4QI (match_dup 2)
8553                 (parallel [(const_int 1)
8554                            (const_int 3)
8555                            (const_int 5)
8556                            (const_int 7)]))))))]
8557   "TARGET_SSSE3"
8558   "pmaddubsw\t{%2, %0|%0, %2}"
8559   [(set_attr "type" "sseiadd")
8560    (set_attr "prefix_extra" "1")
8561    (set_attr "mode" "DI")])
8562
8563 (define_expand "ssse3_pmulhrswv8hi3"
8564   [(set (match_operand:V8HI 0 "register_operand" "")
8565         (truncate:V8HI
8566           (lshiftrt:V8SI
8567             (plus:V8SI
8568               (lshiftrt:V8SI
8569                 (mult:V8SI
8570                   (sign_extend:V8SI
8571                     (match_operand:V8HI 1 "nonimmediate_operand" ""))
8572                   (sign_extend:V8SI
8573                     (match_operand:V8HI 2 "nonimmediate_operand" "")))
8574                 (const_int 14))
8575               (const_vector:V8HI [(const_int 1) (const_int 1)
8576                                   (const_int 1) (const_int 1)
8577                                   (const_int 1) (const_int 1)
8578                                   (const_int 1) (const_int 1)]))
8579             (const_int 1))))]
8580   "TARGET_SSSE3"
8581   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
8582
8583 (define_insn "*avx_pmulhrswv8hi3"
8584   [(set (match_operand:V8HI 0 "register_operand" "=x")
8585         (truncate:V8HI
8586           (lshiftrt:V8SI
8587             (plus:V8SI
8588               (lshiftrt:V8SI
8589                 (mult:V8SI
8590                   (sign_extend:V8SI
8591                     (match_operand:V8HI 1 "nonimmediate_operand" "%x"))
8592                   (sign_extend:V8SI
8593                     (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
8594                 (const_int 14))
8595               (const_vector:V8HI [(const_int 1) (const_int 1)
8596                                   (const_int 1) (const_int 1)
8597                                   (const_int 1) (const_int 1)
8598                                   (const_int 1) (const_int 1)]))
8599             (const_int 1))))]
8600   "TARGET_AVX && ix86_binary_operator_ok (MULT, V8HImode, operands)"
8601   "vpmulhrsw\t{%2, %1, %0|%0, %1, %2}"
8602   [(set_attr "type" "sseimul")
8603    (set_attr "prefix" "vex")
8604    (set_attr "mode" "TI")])
8605
8606 (define_insn "*ssse3_pmulhrswv8hi3"
8607   [(set (match_operand:V8HI 0 "register_operand" "=x")
8608         (truncate:V8HI
8609           (lshiftrt:V8SI
8610             (plus:V8SI
8611               (lshiftrt:V8SI
8612                 (mult:V8SI
8613                   (sign_extend:V8SI
8614                     (match_operand:V8HI 1 "nonimmediate_operand" "%0"))
8615                   (sign_extend:V8SI
8616                     (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
8617                 (const_int 14))
8618               (const_vector:V8HI [(const_int 1) (const_int 1)
8619                                   (const_int 1) (const_int 1)
8620                                   (const_int 1) (const_int 1)
8621                                   (const_int 1) (const_int 1)]))
8622             (const_int 1))))]
8623   "TARGET_SSSE3 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
8624   "pmulhrsw\t{%2, %0|%0, %2}"
8625   [(set_attr "type" "sseimul")
8626    (set_attr "prefix_data16" "1")
8627    (set_attr "prefix_extra" "1")
8628    (set_attr "mode" "TI")])
8629
8630 (define_expand "ssse3_pmulhrswv4hi3"
8631   [(set (match_operand:V4HI 0 "register_operand" "")
8632         (truncate:V4HI
8633           (lshiftrt:V4SI
8634             (plus:V4SI
8635               (lshiftrt:V4SI
8636                 (mult:V4SI
8637                   (sign_extend:V4SI
8638                     (match_operand:V4HI 1 "nonimmediate_operand" ""))
8639                   (sign_extend:V4SI
8640                     (match_operand:V4HI 2 "nonimmediate_operand" "")))
8641                 (const_int 14))
8642               (const_vector:V4HI [(const_int 1) (const_int 1)
8643                                   (const_int 1) (const_int 1)]))
8644             (const_int 1))))]
8645   "TARGET_SSSE3"
8646   "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
8647
8648 (define_insn "*ssse3_pmulhrswv4hi3"
8649   [(set (match_operand:V4HI 0 "register_operand" "=y")
8650         (truncate:V4HI
8651           (lshiftrt:V4SI
8652             (plus:V4SI
8653               (lshiftrt:V4SI
8654                 (mult:V4SI
8655                   (sign_extend:V4SI
8656                     (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
8657                   (sign_extend:V4SI
8658                     (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
8659                 (const_int 14))
8660               (const_vector:V4HI [(const_int 1) (const_int 1)
8661                                   (const_int 1) (const_int 1)]))
8662             (const_int 1))))]
8663   "TARGET_SSSE3 && ix86_binary_operator_ok (MULT, V4HImode, operands)"
8664   "pmulhrsw\t{%2, %0|%0, %2}"
8665   [(set_attr "type" "sseimul")
8666    (set_attr "prefix_extra" "1")
8667    (set_attr "mode" "DI")])
8668
8669 (define_insn "*avx_pshufbv16qi3"
8670   [(set (match_operand:V16QI 0 "register_operand" "=x")
8671         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
8672                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")]
8673                       UNSPEC_PSHUFB))]
8674   "TARGET_AVX"
8675   "vpshufb\t{%2, %1, %0|%0, %1, %2}";
8676   [(set_attr "type" "sselog1")
8677    (set_attr "prefix" "vex")
8678    (set_attr "mode" "TI")])
8679
8680 (define_insn "ssse3_pshufbv16qi3"
8681   [(set (match_operand:V16QI 0 "register_operand" "=x")
8682         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "0")
8683                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")]
8684                       UNSPEC_PSHUFB))]
8685   "TARGET_SSSE3"
8686   "pshufb\t{%2, %0|%0, %2}";
8687   [(set_attr "type" "sselog1")
8688    (set_attr "prefix_data16" "1")
8689    (set_attr "prefix_extra" "1")
8690    (set_attr "mode" "TI")])
8691
8692 (define_insn "ssse3_pshufbv8qi3"
8693   [(set (match_operand:V8QI 0 "register_operand" "=y")
8694         (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "0")
8695                       (match_operand:V8QI 2 "nonimmediate_operand" "ym")]
8696                      UNSPEC_PSHUFB))]
8697   "TARGET_SSSE3"
8698   "pshufb\t{%2, %0|%0, %2}";
8699   [(set_attr "type" "sselog1")
8700    (set_attr "prefix_extra" "1")
8701    (set_attr "mode" "DI")])
8702
8703 (define_insn "*avx_psign<mode>3"
8704   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
8705         (unspec:SSEMODE124
8706           [(match_operand:SSEMODE124 1 "register_operand" "x")
8707            (match_operand:SSEMODE124 2 "nonimmediate_operand" "xm")]
8708           UNSPEC_PSIGN))]
8709   "TARGET_AVX"
8710   "vpsign<ssevecsize>\t{%2, %1, %0|%0, %1, %2}";
8711   [(set_attr "type" "sselog1")
8712    (set_attr "prefix" "vex")
8713    (set_attr "mode" "TI")])
8714
8715 (define_insn "ssse3_psign<mode>3"
8716   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
8717         (unspec:SSEMODE124
8718           [(match_operand:SSEMODE124 1 "register_operand" "0")
8719            (match_operand:SSEMODE124 2 "nonimmediate_operand" "xm")]
8720           UNSPEC_PSIGN))]
8721   "TARGET_SSSE3"
8722   "psign<ssevecsize>\t{%2, %0|%0, %2}";
8723   [(set_attr "type" "sselog1")
8724    (set_attr "prefix_data16" "1")
8725    (set_attr "prefix_extra" "1")
8726    (set_attr "mode" "TI")])
8727
8728 (define_insn "ssse3_psign<mode>3"
8729   [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
8730         (unspec:MMXMODEI
8731           [(match_operand:MMXMODEI 1 "register_operand" "0")
8732            (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")]
8733           UNSPEC_PSIGN))]
8734   "TARGET_SSSE3"
8735   "psign<mmxvecsize>\t{%2, %0|%0, %2}";
8736   [(set_attr "type" "sselog1")
8737    (set_attr "prefix_extra" "1")
8738    (set_attr "mode" "DI")])
8739
8740 (define_insn "*avx_palignrti"
8741   [(set (match_operand:TI 0 "register_operand" "=x")
8742         (unspec:TI [(match_operand:TI 1 "register_operand" "x")
8743                     (match_operand:TI 2 "nonimmediate_operand" "xm")
8744                     (match_operand:SI 3 "const_0_to_255_mul_8_operand" "n")]
8745                    UNSPEC_PALIGNR))]
8746   "TARGET_AVX"
8747 {
8748   operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
8749   return "vpalignr\t{%3, %2, %1, %0|%0, %1, %2, %3}";
8750 }
8751   [(set_attr "type" "sseishft")
8752    (set_attr "prefix" "vex")
8753    (set_attr "mode" "TI")])
8754
8755 (define_insn "ssse3_palignrti"
8756   [(set (match_operand:TI 0 "register_operand" "=x")
8757         (unspec:TI [(match_operand:TI 1 "register_operand" "0")
8758                     (match_operand:TI 2 "nonimmediate_operand" "xm")
8759                     (match_operand:SI 3 "const_0_to_255_mul_8_operand" "n")]
8760                    UNSPEC_PALIGNR))]
8761   "TARGET_SSSE3"
8762 {
8763   operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
8764   return "palignr\t{%3, %2, %0|%0, %2, %3}";
8765 }
8766   [(set_attr "type" "sseishft")
8767    (set_attr "prefix_data16" "1")
8768    (set_attr "prefix_extra" "1")
8769    (set_attr "mode" "TI")])
8770
8771 (define_insn "ssse3_palignrdi"
8772   [(set (match_operand:DI 0 "register_operand" "=y")
8773         (unspec:DI [(match_operand:DI 1 "register_operand" "0")
8774                     (match_operand:DI 2 "nonimmediate_operand" "ym")
8775                     (match_operand:SI 3 "const_0_to_255_mul_8_operand" "n")]
8776                    UNSPEC_PALIGNR))]
8777   "TARGET_SSSE3"
8778 {
8779   operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
8780   return "palignr\t{%3, %2, %0|%0, %2, %3}";
8781 }
8782   [(set_attr "type" "sseishft")
8783    (set_attr "prefix_extra" "1")
8784    (set_attr "mode" "DI")])
8785
8786 (define_insn "abs<mode>2"
8787   [(set (match_operand:SSEMODE124 0 "register_operand" "=x")
8788         (abs:SSEMODE124 (match_operand:SSEMODE124 1 "nonimmediate_operand" "xm")))]
8789   "TARGET_SSSE3"
8790   "%vpabs<ssevecsize>\t{%1, %0|%0, %1}"
8791   [(set_attr "type" "sselog1")
8792    (set_attr "prefix_data16" "1")
8793    (set_attr "prefix_extra" "1")
8794    (set_attr "prefix" "maybe_vex")
8795    (set_attr "mode" "TI")])
8796
8797 (define_insn "abs<mode>2"
8798   [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
8799         (abs:MMXMODEI (match_operand:MMXMODEI 1 "nonimmediate_operand" "ym")))]
8800   "TARGET_SSSE3"
8801   "pabs<mmxvecsize>\t{%1, %0|%0, %1}";
8802   [(set_attr "type" "sselog1")
8803    (set_attr "prefix_extra" "1")
8804    (set_attr "mode" "DI")])
8805
8806 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8807 ;;
8808 ;; AMD SSE4A instructions
8809 ;;
8810 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8811
8812 (define_insn "sse4a_movnt<mode>"
8813   [(set (match_operand:MODEF 0 "memory_operand" "=m")
8814         (unspec:MODEF
8815           [(match_operand:MODEF 1 "register_operand" "x")]
8816           UNSPEC_MOVNT))]
8817   "TARGET_SSE4A"
8818   "movnts<ssemodefsuffix>\t{%1, %0|%0, %1}"
8819   [(set_attr "type" "ssemov")
8820    (set_attr "mode" "<MODE>")])
8821
8822 (define_insn "sse4a_vmmovnt<mode>"
8823   [(set (match_operand:<ssescalarmode> 0 "memory_operand" "=m")
8824         (unspec:<ssescalarmode>
8825           [(vec_select:<ssescalarmode>
8826              (match_operand:SSEMODEF2P 1 "register_operand" "x")
8827              (parallel [(const_int 0)]))]
8828           UNSPEC_MOVNT))]
8829   "TARGET_SSE4A"
8830   "movnts<ssemodesuffixf2c>\t{%1, %0|%0, %1}"
8831   [(set_attr "type" "ssemov")
8832    (set_attr "mode" "<ssescalarmode>")])
8833
8834 (define_insn "sse4a_extrqi"
8835   [(set (match_operand:V2DI 0 "register_operand" "=x")
8836         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
8837                       (match_operand 2 "const_int_operand" "")
8838                       (match_operand 3 "const_int_operand" "")]
8839                      UNSPEC_EXTRQI))]
8840   "TARGET_SSE4A"
8841   "extrq\t{%3, %2, %0|%0, %2, %3}"
8842   [(set_attr "type" "sse")
8843    (set_attr "prefix_data16" "1")
8844    (set_attr "mode" "TI")])
8845
8846 (define_insn "sse4a_extrq"
8847   [(set (match_operand:V2DI 0 "register_operand" "=x")
8848         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
8849                       (match_operand:V16QI 2 "register_operand" "x")]
8850                      UNSPEC_EXTRQ))]
8851   "TARGET_SSE4A"
8852   "extrq\t{%2, %0|%0, %2}"
8853   [(set_attr "type" "sse")
8854    (set_attr "prefix_data16" "1")
8855    (set_attr "mode" "TI")])
8856
8857 (define_insn "sse4a_insertqi"
8858   [(set (match_operand:V2DI 0 "register_operand" "=x")
8859         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
8860                       (match_operand:V2DI 2 "register_operand" "x")
8861                       (match_operand 3 "const_int_operand" "")
8862                       (match_operand 4 "const_int_operand" "")]
8863                      UNSPEC_INSERTQI))]
8864   "TARGET_SSE4A"
8865   "insertq\t{%4, %3, %2, %0|%0, %2, %3, %4}"
8866   [(set_attr "type" "sseins")
8867    (set_attr "prefix_rep" "1")
8868    (set_attr "mode" "TI")])
8869
8870 (define_insn "sse4a_insertq"
8871   [(set (match_operand:V2DI 0 "register_operand" "=x")
8872         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
8873                       (match_operand:V2DI 2 "register_operand" "x")]
8874                      UNSPEC_INSERTQ))]
8875   "TARGET_SSE4A"
8876   "insertq\t{%2, %0|%0, %2}"
8877   [(set_attr "type" "sseins")
8878    (set_attr "prefix_rep" "1")
8879    (set_attr "mode" "TI")])
8880
8881 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8882 ;;
8883 ;; Intel SSE4.1 instructions
8884 ;;
8885 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8886
8887 (define_insn "avx_blendp<avxmodesuffixf2c><avxmodesuffix>"
8888   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
8889         (vec_merge:AVXMODEF2P
8890           (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")
8891           (match_operand:AVXMODEF2P 1 "register_operand" "x")
8892           (match_operand:SI 3 "const_0_to_<blendbits>_operand" "n")))]
8893   "TARGET_AVX"
8894   "vblendp<avxmodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
8895   [(set_attr "type" "ssemov")
8896    (set_attr "prefix" "vex")
8897    (set_attr "mode" "<avxvecmode>")])
8898
8899 (define_insn "avx_blendvp<avxmodesuffixf2c><avxmodesuffix>"
8900   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
8901         (unspec:AVXMODEF2P
8902           [(match_operand:AVXMODEF2P 1 "register_operand" "x")
8903            (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")
8904            (match_operand:AVXMODEF2P 3 "register_operand" "x")]
8905           UNSPEC_BLENDV))]
8906   "TARGET_AVX"
8907   "vblendvp<avxmodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
8908   [(set_attr "type" "ssemov")
8909    (set_attr "prefix" "vex")
8910    (set_attr "mode" "<avxvecmode>")])
8911
8912 (define_insn "sse4_1_blendp<ssemodesuffixf2c>"
8913   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
8914         (vec_merge:SSEMODEF2P
8915           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")
8916           (match_operand:SSEMODEF2P 1 "register_operand" "0")
8917           (match_operand:SI 3 "const_0_to_<blendbits>_operand" "n")))]
8918   "TARGET_SSE4_1"
8919   "blendp<ssemodesuffixf2c>\t{%3, %2, %0|%0, %2, %3}"
8920   [(set_attr "type" "ssemov")
8921    (set_attr "prefix_extra" "1")
8922    (set_attr "mode" "<MODE>")])
8923
8924 (define_insn "sse4_1_blendvp<ssemodesuffixf2c>"
8925   [(set (match_operand:SSEMODEF2P 0 "reg_not_xmm0_operand" "=x")
8926         (unspec:SSEMODEF2P
8927           [(match_operand:SSEMODEF2P 1 "reg_not_xmm0_operand" "0")
8928            (match_operand:SSEMODEF2P 2 "nonimm_not_xmm0_operand" "xm")
8929            (match_operand:SSEMODEF2P 3 "register_operand" "Yz")]
8930           UNSPEC_BLENDV))]
8931   "TARGET_SSE4_1"
8932   "blendvp<ssemodesuffixf2c>\t{%3, %2, %0|%0, %2, %3}"
8933   [(set_attr "type" "ssemov")
8934    (set_attr "prefix_extra" "1")
8935    (set_attr "mode" "<MODE>")])
8936
8937 (define_insn "avx_dpp<avxmodesuffixf2c><avxmodesuffix>"
8938   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
8939         (unspec:AVXMODEF2P
8940           [(match_operand:AVXMODEF2P 1 "nonimmediate_operand" "%x")
8941            (match_operand:AVXMODEF2P 2 "nonimmediate_operand" "xm")
8942            (match_operand:SI 3 "const_0_to_255_operand" "n")]
8943           UNSPEC_DP))]
8944   "TARGET_AVX"
8945   "vdpp<avxmodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
8946   [(set_attr "type" "ssemul")
8947    (set_attr "prefix" "vex")
8948    (set_attr "mode" "<avxvecmode>")])
8949
8950 (define_insn "sse4_1_dpp<ssemodesuffixf2c>"
8951   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
8952         (unspec:SSEMODEF2P
8953           [(match_operand:SSEMODEF2P 1 "nonimmediate_operand" "%0")
8954            (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")
8955            (match_operand:SI 3 "const_0_to_255_operand" "n")]
8956           UNSPEC_DP))]
8957   "TARGET_SSE4_1"
8958   "dpp<ssemodesuffixf2c>\t{%3, %2, %0|%0, %2, %3}"
8959   [(set_attr "type" "ssemul")
8960    (set_attr "prefix_extra" "1")
8961    (set_attr "mode" "<MODE>")])
8962
8963 (define_insn "sse4_1_movntdqa"
8964   [(set (match_operand:V2DI 0 "register_operand" "=x")
8965         (unspec:V2DI [(match_operand:V2DI 1 "memory_operand" "m")]
8966                      UNSPEC_MOVNTDQA))]
8967   "TARGET_SSE4_1"
8968   "%vmovntdqa\t{%1, %0|%0, %1}"
8969   [(set_attr "type" "ssecvt")
8970    (set_attr "prefix_extra" "1")
8971    (set_attr "prefix" "maybe_vex")
8972    (set_attr "mode" "TI")])
8973
8974 (define_insn "*avx_mpsadbw"
8975   [(set (match_operand:V16QI 0 "register_operand" "=x")
8976         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
8977                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")
8978                        (match_operand:SI 3 "const_0_to_255_operand" "n")]
8979                       UNSPEC_MPSADBW))]
8980   "TARGET_AVX"
8981   "vmpsadbw\t{%3, %2, %1, %0|%0, %1, %2, %3}"
8982   [(set_attr "type" "sselog1")
8983    (set_attr "prefix" "vex")
8984    (set_attr "mode" "TI")])
8985
8986 (define_insn "sse4_1_mpsadbw"
8987   [(set (match_operand:V16QI 0 "register_operand" "=x")
8988         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "0")
8989                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")
8990                        (match_operand:SI 3 "const_0_to_255_operand" "n")]
8991                       UNSPEC_MPSADBW))]
8992   "TARGET_SSE4_1"
8993   "mpsadbw\t{%3, %2, %0|%0, %2, %3}"
8994   [(set_attr "type" "sselog1")
8995    (set_attr "prefix_extra" "1")
8996    (set_attr "mode" "TI")])
8997
8998 (define_insn "*avx_packusdw"
8999   [(set (match_operand:V8HI 0 "register_operand" "=x")
9000         (vec_concat:V8HI
9001           (us_truncate:V4HI
9002             (match_operand:V4SI 1 "register_operand" "x"))
9003           (us_truncate:V4HI
9004             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))))]
9005   "TARGET_AVX"
9006   "vpackusdw\t{%2, %1, %0|%0, %1, %2}"
9007   [(set_attr "type" "sselog")
9008    (set_attr "prefix" "vex")
9009    (set_attr "mode" "TI")])
9010
9011 (define_insn "sse4_1_packusdw"
9012   [(set (match_operand:V8HI 0 "register_operand" "=x")
9013         (vec_concat:V8HI
9014           (us_truncate:V4HI
9015             (match_operand:V4SI 1 "register_operand" "0"))
9016           (us_truncate:V4HI
9017             (match_operand:V4SI 2 "nonimmediate_operand" "xm"))))]
9018   "TARGET_SSE4_1"
9019   "packusdw\t{%2, %0|%0, %2}"
9020   [(set_attr "type" "sselog")
9021    (set_attr "prefix_extra" "1")
9022    (set_attr "mode" "TI")])
9023
9024 (define_insn "*avx_pblendvb"
9025   [(set (match_operand:V16QI 0 "register_operand" "=x")
9026         (unspec:V16QI [(match_operand:V16QI 1 "register_operand"  "x")
9027                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")
9028                        (match_operand:V16QI 3 "register_operand" "x")]
9029                       UNSPEC_BLENDV))]
9030   "TARGET_AVX"
9031   "vpblendvb\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9032   [(set_attr "type" "ssemov")
9033    (set_attr "prefix" "vex")
9034    (set_attr "mode" "TI")])
9035
9036 (define_insn "sse4_1_pblendvb"
9037   [(set (match_operand:V16QI 0 "reg_not_xmm0_operand" "=x")
9038         (unspec:V16QI [(match_operand:V16QI 1 "reg_not_xmm0_operand"  "0")
9039                        (match_operand:V16QI 2 "nonimm_not_xmm0_operand" "xm")
9040                        (match_operand:V16QI 3 "register_operand" "Yz")]
9041                       UNSPEC_BLENDV))]
9042   "TARGET_SSE4_1"
9043   "pblendvb\t{%3, %2, %0|%0, %2, %3}"
9044   [(set_attr "type" "ssemov")
9045    (set_attr "prefix_extra" "1")
9046    (set_attr "mode" "TI")])
9047
9048 (define_insn "*avx_pblendw"
9049   [(set (match_operand:V8HI 0 "register_operand" "=x")
9050         (vec_merge:V8HI
9051           (match_operand:V8HI 2 "nonimmediate_operand" "xm")
9052           (match_operand:V8HI 1 "register_operand" "x")
9053           (match_operand:SI 3 "const_0_to_255_operand" "n")))]
9054   "TARGET_AVX"
9055   "vpblendw\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9056   [(set_attr "type" "ssemov")
9057    (set_attr "prefix" "vex")
9058    (set_attr "mode" "TI")])
9059
9060 (define_insn "sse4_1_pblendw"
9061   [(set (match_operand:V8HI 0 "register_operand" "=x")
9062         (vec_merge:V8HI
9063           (match_operand:V8HI 2 "nonimmediate_operand" "xm")
9064           (match_operand:V8HI 1 "register_operand" "0")
9065           (match_operand:SI 3 "const_0_to_255_operand" "n")))]
9066   "TARGET_SSE4_1"
9067   "pblendw\t{%3, %2, %0|%0, %2, %3}"
9068   [(set_attr "type" "ssemov")
9069    (set_attr "prefix_extra" "1")
9070    (set_attr "mode" "TI")])
9071
9072 (define_insn "sse4_1_phminposuw"
9073   [(set (match_operand:V8HI 0 "register_operand" "=x")
9074         (unspec:V8HI [(match_operand:V8HI 1 "nonimmediate_operand" "xm")]
9075                      UNSPEC_PHMINPOSUW))]
9076   "TARGET_SSE4_1"
9077   "%vphminposuw\t{%1, %0|%0, %1}"
9078   [(set_attr "type" "sselog1")
9079    (set_attr "prefix_extra" "1")
9080    (set_attr "prefix" "maybe_vex")
9081    (set_attr "mode" "TI")])
9082
9083 (define_insn "sse4_1_extendv8qiv8hi2"
9084   [(set (match_operand:V8HI 0 "register_operand" "=x")
9085         (sign_extend:V8HI
9086           (vec_select:V8QI
9087             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9088             (parallel [(const_int 0)
9089                        (const_int 1)
9090                        (const_int 2)
9091                        (const_int 3)
9092                        (const_int 4)
9093                        (const_int 5)
9094                        (const_int 6)
9095                        (const_int 7)]))))]
9096   "TARGET_SSE4_1"
9097   "%vpmovsxbw\t{%1, %0|%0, %1}"
9098   [(set_attr "type" "ssemov")
9099    (set_attr "prefix_extra" "1")
9100    (set_attr "prefix" "maybe_vex")
9101    (set_attr "mode" "TI")])
9102
9103 (define_insn "sse4_1_extendv4qiv4si2"
9104   [(set (match_operand:V4SI 0 "register_operand" "=x")
9105         (sign_extend:V4SI
9106           (vec_select:V4QI
9107             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9108             (parallel [(const_int 0)
9109                        (const_int 1)
9110                        (const_int 2)
9111                        (const_int 3)]))))]
9112   "TARGET_SSE4_1"
9113   "%vpmovsxbd\t{%1, %0|%0, %1}"
9114   [(set_attr "type" "ssemov")
9115    (set_attr "prefix_extra" "1")
9116    (set_attr "prefix" "maybe_vex")
9117    (set_attr "mode" "TI")])
9118
9119 (define_insn "sse4_1_extendv2qiv2di2"
9120   [(set (match_operand:V2DI 0 "register_operand" "=x")
9121         (sign_extend:V2DI
9122           (vec_select:V2QI
9123             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9124             (parallel [(const_int 0)
9125                        (const_int 1)]))))]
9126   "TARGET_SSE4_1"
9127   "%vpmovsxbq\t{%1, %0|%0, %1}"
9128   [(set_attr "type" "ssemov")
9129    (set_attr "prefix_extra" "1")
9130    (set_attr "prefix" "maybe_vex")
9131    (set_attr "mode" "TI")])
9132
9133 (define_insn "sse4_1_extendv4hiv4si2"
9134   [(set (match_operand:V4SI 0 "register_operand" "=x")
9135         (sign_extend:V4SI
9136           (vec_select:V4HI
9137             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9138             (parallel [(const_int 0)
9139                        (const_int 1)
9140                        (const_int 2)
9141                        (const_int 3)]))))]
9142   "TARGET_SSE4_1"
9143   "%vpmovsxwd\t{%1, %0|%0, %1}"
9144   [(set_attr "type" "ssemov")
9145    (set_attr "prefix_extra" "1")
9146    (set_attr "prefix" "maybe_vex")
9147    (set_attr "mode" "TI")])
9148
9149 (define_insn "sse4_1_extendv2hiv2di2"
9150   [(set (match_operand:V2DI 0 "register_operand" "=x")
9151         (sign_extend:V2DI
9152           (vec_select:V2HI
9153             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9154             (parallel [(const_int 0)
9155                        (const_int 1)]))))]
9156   "TARGET_SSE4_1"
9157   "%vpmovsxwq\t{%1, %0|%0, %1}"
9158   [(set_attr "type" "ssemov")
9159    (set_attr "prefix_extra" "1")
9160    (set_attr "prefix" "maybe_vex")
9161    (set_attr "mode" "TI")])
9162
9163 (define_insn "sse4_1_extendv2siv2di2"
9164   [(set (match_operand:V2DI 0 "register_operand" "=x")
9165         (sign_extend:V2DI
9166           (vec_select:V2SI
9167             (match_operand:V4SI 1 "nonimmediate_operand" "xm")
9168             (parallel [(const_int 0)
9169                        (const_int 1)]))))]
9170   "TARGET_SSE4_1"
9171   "%vpmovsxdq\t{%1, %0|%0, %1}"
9172   [(set_attr "type" "ssemov")
9173    (set_attr "prefix_extra" "1")
9174    (set_attr "prefix" "maybe_vex")
9175    (set_attr "mode" "TI")])
9176
9177 (define_insn "sse4_1_zero_extendv8qiv8hi2"
9178   [(set (match_operand:V8HI 0 "register_operand" "=x")
9179         (zero_extend:V8HI
9180           (vec_select:V8QI
9181             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9182             (parallel [(const_int 0)
9183                        (const_int 1)
9184                        (const_int 2)
9185                        (const_int 3)
9186                        (const_int 4)
9187                        (const_int 5)
9188                        (const_int 6)
9189                        (const_int 7)]))))]
9190   "TARGET_SSE4_1"
9191   "%vpmovzxbw\t{%1, %0|%0, %1}"
9192   [(set_attr "type" "ssemov")
9193    (set_attr "prefix_extra" "1")
9194    (set_attr "prefix" "maybe_vex")
9195    (set_attr "mode" "TI")])
9196
9197 (define_insn "sse4_1_zero_extendv4qiv4si2"
9198   [(set (match_operand:V4SI 0 "register_operand" "=x")
9199         (zero_extend:V4SI
9200           (vec_select:V4QI
9201             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9202             (parallel [(const_int 0)
9203                        (const_int 1)
9204                        (const_int 2)
9205                        (const_int 3)]))))]
9206   "TARGET_SSE4_1"
9207   "%vpmovzxbd\t{%1, %0|%0, %1}"
9208   [(set_attr "type" "ssemov")
9209    (set_attr "prefix_extra" "1")
9210    (set_attr "prefix" "maybe_vex")
9211    (set_attr "mode" "TI")])
9212
9213 (define_insn "sse4_1_zero_extendv2qiv2di2"
9214   [(set (match_operand:V2DI 0 "register_operand" "=x")
9215         (zero_extend:V2DI
9216           (vec_select:V2QI
9217             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9218             (parallel [(const_int 0)
9219                        (const_int 1)]))))]
9220   "TARGET_SSE4_1"
9221   "%vpmovzxbq\t{%1, %0|%0, %1}"
9222   [(set_attr "type" "ssemov")
9223    (set_attr "prefix_extra" "1")
9224    (set_attr "prefix" "maybe_vex")
9225    (set_attr "mode" "TI")])
9226
9227 (define_insn "sse4_1_zero_extendv4hiv4si2"
9228   [(set (match_operand:V4SI 0 "register_operand" "=x")
9229         (zero_extend:V4SI
9230           (vec_select:V4HI
9231             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9232             (parallel [(const_int 0)
9233                        (const_int 1)
9234                        (const_int 2)
9235                        (const_int 3)]))))]
9236   "TARGET_SSE4_1"
9237   "%vpmovzxwd\t{%1, %0|%0, %1}"
9238   [(set_attr "type" "ssemov")
9239    (set_attr "prefix_extra" "1")
9240    (set_attr "prefix" "maybe_vex")
9241    (set_attr "mode" "TI")])
9242
9243 (define_insn "sse4_1_zero_extendv2hiv2di2"
9244   [(set (match_operand:V2DI 0 "register_operand" "=x")
9245         (zero_extend:V2DI
9246           (vec_select:V2HI
9247             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9248             (parallel [(const_int 0)
9249                        (const_int 1)]))))]
9250   "TARGET_SSE4_1"
9251   "%vpmovzxwq\t{%1, %0|%0, %1}"
9252   [(set_attr "type" "ssemov")
9253    (set_attr "prefix_extra" "1")
9254    (set_attr "prefix" "maybe_vex")
9255    (set_attr "mode" "TI")])
9256
9257 (define_insn "sse4_1_zero_extendv2siv2di2"
9258   [(set (match_operand:V2DI 0 "register_operand" "=x")
9259         (zero_extend:V2DI
9260           (vec_select:V2SI
9261             (match_operand:V4SI 1 "nonimmediate_operand" "xm")
9262             (parallel [(const_int 0)
9263                        (const_int 1)]))))]
9264   "TARGET_SSE4_1"
9265   "%vpmovzxdq\t{%1, %0|%0, %1}"
9266   [(set_attr "type" "ssemov")
9267    (set_attr "prefix_extra" "1")
9268    (set_attr "prefix" "maybe_vex")
9269    (set_attr "mode" "TI")])
9270
9271 ;; ptestps/ptestpd are very similar to comiss and ucomiss when
9272 ;; setting FLAGS_REG. But it is not a really compare instruction.
9273 (define_insn "avx_vtestp<avxmodesuffixf2c><avxmodesuffix>"
9274   [(set (reg:CC FLAGS_REG)
9275         (unspec:CC [(match_operand:AVXMODEF2P 0 "register_operand" "x")
9276                     (match_operand:AVXMODEF2P 1 "nonimmediate_operand" "xm")]
9277                    UNSPEC_VTESTP))]
9278   "TARGET_AVX"
9279   "vtestp<avxmodesuffixf2c>\t{%1, %0|%0, %1}"
9280   [(set_attr "type" "ssecomi")
9281    (set_attr "prefix" "vex")
9282    (set_attr "mode" "<MODE>")])
9283
9284 ;; ptest is very similar to comiss and ucomiss when setting FLAGS_REG.
9285 ;; But it is not a really compare instruction.
9286 (define_insn "avx_ptest256"
9287   [(set (reg:CC FLAGS_REG)
9288         (unspec:CC [(match_operand:V4DI 0 "register_operand" "x")
9289                     (match_operand:V4DI 1 "nonimmediate_operand" "xm")]
9290                    UNSPEC_PTEST))]
9291   "TARGET_AVX"
9292   "vptest\t{%1, %0|%0, %1}"
9293   [(set_attr "type" "ssecomi")
9294    (set_attr "prefix" "vex")
9295    (set_attr "mode" "OI")])
9296
9297 (define_insn "sse4_1_ptest"
9298   [(set (reg:CC FLAGS_REG)
9299         (unspec:CC [(match_operand:V2DI 0 "register_operand" "x")
9300                     (match_operand:V2DI 1 "nonimmediate_operand" "xm")]
9301                    UNSPEC_PTEST))]
9302   "TARGET_SSE4_1"
9303   "%vptest\t{%1, %0|%0, %1}"
9304   [(set_attr "type" "ssecomi")
9305    (set_attr "prefix_extra" "1")
9306    (set_attr "prefix" "maybe_vex")
9307    (set_attr "mode" "TI")])
9308
9309 (define_insn "avx_roundp<avxmodesuffixf2c>256"
9310   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "=x")
9311         (unspec:AVX256MODEF2P
9312           [(match_operand:AVX256MODEF2P 1 "nonimmediate_operand" "xm")
9313            (match_operand:SI 2 "const_0_to_15_operand" "n")]
9314           UNSPEC_ROUND))]
9315   "TARGET_AVX"
9316   "vroundp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
9317   [(set_attr "type" "ssecvt")
9318    (set_attr "prefix" "vex")
9319    (set_attr "mode" "<MODE>")])
9320
9321 (define_insn "sse4_1_roundp<ssemodesuffixf2c>"
9322   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
9323         (unspec:SSEMODEF2P
9324           [(match_operand:SSEMODEF2P 1 "nonimmediate_operand" "xm")
9325            (match_operand:SI 2 "const_0_to_15_operand" "n")]
9326           UNSPEC_ROUND))]
9327   "TARGET_ROUND"
9328   "%vroundp<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
9329   [(set_attr "type" "ssecvt")
9330    (set_attr "prefix_extra" "1")
9331    (set_attr "prefix" "maybe_vex")
9332    (set_attr "mode" "<MODE>")])
9333
9334 (define_insn "*avx_rounds<ssemodesuffixf2c>"
9335   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
9336         (vec_merge:SSEMODEF2P
9337           (unspec:SSEMODEF2P
9338             [(match_operand:SSEMODEF2P 2 "register_operand" "x")
9339              (match_operand:SI 3 "const_0_to_15_operand" "n")]
9340             UNSPEC_ROUND)
9341           (match_operand:SSEMODEF2P 1 "register_operand" "x")
9342           (const_int 1)))]
9343   "TARGET_AVX"
9344   "vrounds<ssemodesuffixf2c>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9345   [(set_attr "type" "ssecvt")
9346    (set_attr "prefix" "vex")
9347    (set_attr "mode" "<MODE>")])
9348
9349 (define_insn "sse4_1_rounds<ssemodesuffixf2c>"
9350   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
9351         (vec_merge:SSEMODEF2P
9352           (unspec:SSEMODEF2P
9353             [(match_operand:SSEMODEF2P 2 "register_operand" "x")
9354              (match_operand:SI 3 "const_0_to_15_operand" "n")]
9355             UNSPEC_ROUND)
9356           (match_operand:SSEMODEF2P 1 "register_operand" "0")
9357           (const_int 1)))]
9358   "TARGET_ROUND"
9359   "rounds<ssemodesuffixf2c>\t{%3, %2, %0|%0, %2, %3}"
9360   [(set_attr "type" "ssecvt")
9361    (set_attr "prefix_extra" "1")
9362    (set_attr "mode" "<MODE>")])
9363
9364 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9365 ;;
9366 ;; Intel SSE4.2 string/text processing instructions
9367 ;;
9368 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9369
9370 (define_insn_and_split "sse4_2_pcmpestr"
9371   [(set (match_operand:SI 0 "register_operand" "=c,c")
9372         (unspec:SI
9373           [(match_operand:V16QI 2 "reg_not_xmm0_operand" "x,x")
9374            (match_operand:SI 3 "register_operand" "a,a")
9375            (match_operand:V16QI 4 "nonimm_not_xmm0_operand" "x,m")
9376            (match_operand:SI 5 "register_operand" "d,d")
9377            (match_operand:SI 6 "const_0_to_255_operand" "n,n")]
9378           UNSPEC_PCMPESTR))
9379    (set (match_operand:V16QI 1 "register_operand" "=Yz,Yz")
9380         (unspec:V16QI
9381           [(match_dup 2)
9382            (match_dup 3)
9383            (match_dup 4)
9384            (match_dup 5)
9385            (match_dup 6)]
9386           UNSPEC_PCMPESTR))
9387    (set (reg:CC FLAGS_REG)
9388         (unspec:CC
9389           [(match_dup 2)
9390            (match_dup 3)
9391            (match_dup 4)
9392            (match_dup 5)
9393            (match_dup 6)]
9394           UNSPEC_PCMPESTR))]
9395   "TARGET_SSE4_2
9396    && !(reload_completed || reload_in_progress)"
9397   "#"
9398   "&& 1"
9399   [(const_int 0)]
9400 {
9401   int ecx = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[0]));
9402   int xmm0 = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[1]));
9403   int flags = !find_regno_note (curr_insn, REG_UNUSED, FLAGS_REG);
9404
9405   if (ecx)
9406     emit_insn (gen_sse4_2_pcmpestri (operands[0], operands[2],
9407                                      operands[3], operands[4],
9408                                      operands[5], operands[6]));
9409   if (xmm0)
9410     emit_insn (gen_sse4_2_pcmpestrm (operands[1], operands[2],
9411                                      operands[3], operands[4],
9412                                      operands[5], operands[6]));
9413   if (flags && !(ecx || xmm0))
9414     emit_insn (gen_sse4_2_pcmpestr_cconly (NULL, NULL,
9415                                            operands[2], operands[3],
9416                                            operands[4], operands[5],
9417                                            operands[6]));
9418   DONE;
9419 }
9420   [(set_attr "type" "sselog")
9421    (set_attr "prefix_data16" "1")
9422    (set_attr "prefix_extra" "1")
9423    (set_attr "memory" "none,load")
9424    (set_attr "mode" "TI")])
9425
9426 (define_insn "sse4_2_pcmpestri"
9427   [(set (match_operand:SI 0 "register_operand" "=c,c")
9428         (unspec:SI
9429           [(match_operand:V16QI 1 "register_operand" "x,x")
9430            (match_operand:SI 2 "register_operand" "a,a")
9431            (match_operand:V16QI 3 "nonimmediate_operand" "x,m")
9432            (match_operand:SI 4 "register_operand" "d,d")
9433            (match_operand:SI 5 "const_0_to_255_operand" "n,n")]
9434           UNSPEC_PCMPESTR))
9435    (set (reg:CC FLAGS_REG)
9436         (unspec:CC
9437           [(match_dup 1)
9438            (match_dup 2)
9439            (match_dup 3)
9440            (match_dup 4)
9441            (match_dup 5)]
9442           UNSPEC_PCMPESTR))]
9443   "TARGET_SSE4_2"
9444   "%vpcmpestri\t{%5, %3, %1|%1, %3, %5}"
9445   [(set_attr "type" "sselog")
9446    (set_attr "prefix_data16" "1")
9447    (set_attr "prefix_extra" "1")
9448    (set_attr "prefix" "maybe_vex")
9449    (set_attr "memory" "none,load")
9450    (set_attr "mode" "TI")])
9451
9452 (define_insn "sse4_2_pcmpestrm"
9453   [(set (match_operand:V16QI 0 "register_operand" "=Yz,Yz")
9454         (unspec:V16QI
9455           [(match_operand:V16QI 1 "register_operand" "x,x")
9456            (match_operand:SI 2 "register_operand" "a,a")
9457            (match_operand:V16QI 3 "nonimmediate_operand" "x,m")
9458            (match_operand:SI 4 "register_operand" "d,d")
9459            (match_operand:SI 5 "const_0_to_255_operand" "n,n")]
9460           UNSPEC_PCMPESTR))
9461    (set (reg:CC FLAGS_REG)
9462         (unspec:CC
9463           [(match_dup 1)
9464            (match_dup 2)
9465            (match_dup 3)
9466            (match_dup 4)
9467            (match_dup 5)]
9468           UNSPEC_PCMPESTR))]
9469   "TARGET_SSE4_2"
9470   "%vpcmpestrm\t{%5, %3, %1|%1, %3, %5}"
9471   [(set_attr "type" "sselog")
9472    (set_attr "prefix_data16" "1")
9473    (set_attr "prefix_extra" "1")
9474    (set_attr "prefix" "maybe_vex")
9475    (set_attr "memory" "none,load")
9476    (set_attr "mode" "TI")])
9477
9478 (define_insn "sse4_2_pcmpestr_cconly"
9479   [(set (reg:CC FLAGS_REG)
9480         (unspec:CC
9481           [(match_operand:V16QI 2 "register_operand" "x,x,x,x")
9482            (match_operand:SI 3 "register_operand" "a,a,a,a")
9483            (match_operand:V16QI 4 "nonimmediate_operand" "x,m,x,m")
9484            (match_operand:SI 5 "register_operand" "d,d,d,d")
9485            (match_operand:SI 6 "const_0_to_255_operand" "n,n,n,n")]
9486           UNSPEC_PCMPESTR))
9487    (clobber (match_scratch:V16QI 0 "=Yz,Yz,X,X"))
9488    (clobber (match_scratch:SI    1 "= X, X,c,c"))]
9489   "TARGET_SSE4_2"
9490   "@
9491    %vpcmpestrm\t{%6, %4, %2|%2, %4, %6}
9492    %vpcmpestrm\t{%6, %4, %2|%2, %4, %6}
9493    %vpcmpestri\t{%6, %4, %2|%2, %4, %6}
9494    %vpcmpestri\t{%6, %4, %2|%2, %4, %6}"
9495   [(set_attr "type" "sselog")
9496    (set_attr "prefix_data16" "1")
9497    (set_attr "prefix_extra" "1")
9498    (set_attr "memory" "none,load,none,load")
9499    (set_attr "prefix" "maybe_vex")
9500    (set_attr "mode" "TI")])
9501
9502 (define_insn_and_split "sse4_2_pcmpistr"
9503   [(set (match_operand:SI 0 "register_operand" "=c,c")
9504         (unspec:SI
9505           [(match_operand:V16QI 2 "reg_not_xmm0_operand" "x,x")
9506            (match_operand:V16QI 3 "nonimm_not_xmm0_operand" "x,m")
9507            (match_operand:SI 4 "const_0_to_255_operand" "n,n")]
9508           UNSPEC_PCMPISTR))
9509    (set (match_operand:V16QI 1 "register_operand" "=Yz,Yz")
9510         (unspec:V16QI
9511           [(match_dup 2)
9512            (match_dup 3)
9513            (match_dup 4)]
9514           UNSPEC_PCMPISTR))
9515    (set (reg:CC FLAGS_REG)
9516         (unspec:CC
9517           [(match_dup 2)
9518            (match_dup 3)
9519            (match_dup 4)]
9520           UNSPEC_PCMPISTR))]
9521   "TARGET_SSE4_2
9522    && !(reload_completed || reload_in_progress)"
9523   "#"
9524   "&& 1"
9525   [(const_int 0)]
9526 {
9527   int ecx = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[0]));
9528   int xmm0 = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[1]));
9529   int flags = !find_regno_note (curr_insn, REG_UNUSED, FLAGS_REG);
9530
9531   if (ecx)
9532     emit_insn (gen_sse4_2_pcmpistri (operands[0], operands[2],
9533                                      operands[3], operands[4]));
9534   if (xmm0)
9535     emit_insn (gen_sse4_2_pcmpistrm (operands[1], operands[2],
9536                                      operands[3], operands[4]));
9537   if (flags && !(ecx || xmm0))
9538     emit_insn (gen_sse4_2_pcmpistr_cconly (NULL, NULL,
9539                                            operands[2], operands[3],
9540                                            operands[4]));
9541   DONE;
9542 }
9543   [(set_attr "type" "sselog")
9544    (set_attr "prefix_data16" "1")
9545    (set_attr "prefix_extra" "1")
9546    (set_attr "memory" "none,load")
9547    (set_attr "mode" "TI")])
9548
9549 (define_insn "sse4_2_pcmpistri"
9550   [(set (match_operand:SI 0 "register_operand" "=c,c")
9551         (unspec:SI
9552           [(match_operand:V16QI 1 "register_operand" "x,x")
9553            (match_operand:V16QI 2 "nonimmediate_operand" "x,m")
9554            (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
9555           UNSPEC_PCMPISTR))
9556    (set (reg:CC FLAGS_REG)
9557         (unspec:CC
9558           [(match_dup 1)
9559            (match_dup 2)
9560            (match_dup 3)]
9561           UNSPEC_PCMPISTR))]
9562   "TARGET_SSE4_2"
9563   "%vpcmpistri\t{%3, %2, %1|%1, %2, %3}"
9564   [(set_attr "type" "sselog")
9565    (set_attr "prefix_data16" "1")
9566    (set_attr "prefix_extra" "1")
9567    (set_attr "prefix" "maybe_vex")
9568    (set_attr "memory" "none,load")
9569    (set_attr "mode" "TI")])
9570
9571 (define_insn "sse4_2_pcmpistrm"
9572   [(set (match_operand:V16QI 0 "register_operand" "=Yz,Yz")
9573         (unspec:V16QI
9574           [(match_operand:V16QI 1 "register_operand" "x,x")
9575            (match_operand:V16QI 2 "nonimmediate_operand" "x,m")
9576            (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
9577           UNSPEC_PCMPISTR))
9578    (set (reg:CC FLAGS_REG)
9579         (unspec:CC
9580           [(match_dup 1)
9581            (match_dup 2)
9582            (match_dup 3)]
9583           UNSPEC_PCMPISTR))]
9584   "TARGET_SSE4_2"
9585   "%vpcmpistrm\t{%3, %2, %1|%1, %2, %3}"
9586   [(set_attr "type" "sselog")
9587    (set_attr "prefix_data16" "1")
9588    (set_attr "prefix_extra" "1")
9589    (set_attr "prefix" "maybe_vex")
9590    (set_attr "memory" "none,load")
9591    (set_attr "mode" "TI")])
9592
9593 (define_insn "sse4_2_pcmpistr_cconly"
9594   [(set (reg:CC FLAGS_REG)
9595         (unspec:CC
9596           [(match_operand:V16QI 2 "register_operand" "x,x,x,x")
9597            (match_operand:V16QI 3 "nonimmediate_operand" "x,m,x,m")
9598            (match_operand:SI 4 "const_0_to_255_operand" "n,n,n,n")]
9599           UNSPEC_PCMPISTR))
9600    (clobber (match_scratch:V16QI 0 "=Yz,Yz,X,X"))
9601    (clobber (match_scratch:SI    1 "= X, X,c,c"))]
9602   "TARGET_SSE4_2"
9603   "@
9604    %vpcmpistrm\t{%4, %3, %2|%2, %3, %4}
9605    %vpcmpistrm\t{%4, %3, %2|%2, %3, %4}
9606    %vpcmpistri\t{%4, %3, %2|%2, %3, %4}
9607    %vpcmpistri\t{%4, %3, %2|%2, %3, %4}"
9608   [(set_attr "type" "sselog")
9609    (set_attr "prefix_data16" "1")
9610    (set_attr "prefix_extra" "1")
9611    (set_attr "memory" "none,load,none,load")
9612    (set_attr "prefix" "maybe_vex")
9613    (set_attr "mode" "TI")])
9614
9615 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9616 ;;
9617 ;; SSE5 instructions
9618 ;;
9619 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9620
9621 ;; SSE5 parallel integer multiply/add instructions.
9622 ;; Note the instruction does not allow the value being added to be a memory
9623 ;; operation.  However by pretending via the nonimmediate_operand predicate
9624 ;; that it does and splitting it later allows the following to be recognized:
9625 ;;      a[i] = b[i] * c[i] + d[i];
9626 (define_insn "sse5_pmacsww"
9627   [(set (match_operand:V8HI 0 "register_operand" "=x,x,x")
9628         (plus:V8HI
9629          (mult:V8HI
9630           (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,xm")
9631           (match_operand:V8HI 2 "nonimmediate_operand" "x,xm,x"))
9632          (match_operand:V8HI 3 "register_operand" "0,0,0")))]
9633   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 2, true)"
9634   "@
9635    pmacsww\t{%3, %2, %1, %0|%0, %1, %2, %3}
9636    pmacsww\t{%3, %2, %1, %0|%0, %1, %2, %3}
9637    pmacsww\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9638   [(set_attr "type" "ssemuladd")
9639    (set_attr "mode" "TI")])
9640
9641 ;; Split pmacsww with two memory operands into a load and the pmacsww.
9642 (define_split
9643   [(set (match_operand:V8HI 0 "register_operand" "")
9644         (plus:V8HI
9645          (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "")
9646                     (match_operand:V8HI 2 "nonimmediate_operand" ""))
9647          (match_operand:V8HI 3 "nonimmediate_operand" "")))]
9648   "TARGET_SSE5
9649    && !ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)
9650    && ix86_sse5_valid_op_p (operands, insn, 4, false, 2, true)
9651    && !reg_mentioned_p (operands[0], operands[1])
9652    && !reg_mentioned_p (operands[0], operands[2])
9653    && !reg_mentioned_p (operands[0], operands[3])"
9654   [(const_int 0)]
9655 {
9656   ix86_expand_sse5_multiple_memory (operands, 4, V8HImode);
9657   emit_insn (gen_sse5_pmacsww (operands[0], operands[1], operands[2],
9658                                operands[3]));
9659   DONE;
9660 })
9661
9662 (define_insn "sse5_pmacssww"
9663   [(set (match_operand:V8HI 0 "register_operand" "=x,x,x")
9664         (ss_plus:V8HI
9665          (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,m")
9666                     (match_operand:V8HI 2 "nonimmediate_operand" "x,m,x"))
9667          (match_operand:V8HI 3 "register_operand" "0,0,0")))]
9668   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9669   "@
9670    pmacssww\t{%3, %2, %1, %0|%0, %1, %2, %3}
9671    pmacssww\t{%3, %2, %1, %0|%0, %1, %2, %3}
9672    pmacssww\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9673   [(set_attr "type" "ssemuladd")
9674    (set_attr "mode" "TI")])
9675
9676 ;; Note the instruction does not allow the value being added to be a memory
9677 ;; operation.  However by pretending via the nonimmediate_operand predicate
9678 ;; that it does and splitting it later allows the following to be recognized:
9679 ;;      a[i] = b[i] * c[i] + d[i];
9680 (define_insn "sse5_pmacsdd"
9681   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
9682         (plus:V4SI
9683          (mult:V4SI
9684           (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9685           (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x"))
9686          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
9687   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 2, true)"
9688   "@
9689    pmacsdd\t{%3, %2, %1, %0|%0, %1, %2, %3}
9690    pmacsdd\t{%3, %2, %1, %0|%0, %1, %2, %3}
9691    pmacsdd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9692   [(set_attr "type" "ssemuladd")
9693    (set_attr "mode" "TI")])
9694
9695 ;; Split pmacsdd with two memory operands into a load and the pmacsdd.
9696 (define_split
9697   [(set (match_operand:V4SI 0 "register_operand" "")
9698         (plus:V4SI
9699          (mult:V4SI (match_operand:V4SI 1 "nonimmediate_operand" "")
9700                     (match_operand:V4SI 2 "nonimmediate_operand" ""))
9701          (match_operand:V4SI 3 "nonimmediate_operand" "")))]
9702   "TARGET_SSE5
9703    && !ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)
9704    && ix86_sse5_valid_op_p (operands, insn, 4, false, 2, true)
9705    && !reg_mentioned_p (operands[0], operands[1])
9706    && !reg_mentioned_p (operands[0], operands[2])
9707    && !reg_mentioned_p (operands[0], operands[3])"
9708   [(const_int 0)]
9709 {
9710   ix86_expand_sse5_multiple_memory (operands, 4, V4SImode);
9711   emit_insn (gen_sse5_pmacsdd (operands[0], operands[1], operands[2],
9712                                operands[3]));
9713   DONE;
9714 })
9715
9716 (define_insn "sse5_pmacssdd"
9717   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
9718         (ss_plus:V4SI
9719          (mult:V4SI (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9720                     (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x"))
9721          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
9722   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9723   "@
9724    pmacssdd\t{%3, %2, %1, %0|%0, %1, %2, %3}
9725    pmacssdd\t{%3, %2, %1, %0|%0, %1, %2, %3}
9726    pmacssdd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9727   [(set_attr "type" "ssemuladd")
9728    (set_attr "mode" "TI")])
9729
9730 (define_insn "sse5_pmacssdql"
9731   [(set (match_operand:V2DI 0 "register_operand" "=x,x,x")
9732         (ss_plus:V2DI
9733          (mult:V2DI
9734           (sign_extend:V2DI
9735            (vec_select:V2SI
9736             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9737             (parallel [(const_int 1)
9738                        (const_int 3)])))
9739            (vec_select:V2SI
9740             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9741             (parallel [(const_int 1)
9742                        (const_int 3)])))
9743          (match_operand:V2DI 3 "register_operand" "0,0,0")))]
9744   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9745   "@
9746    pmacssdql\t{%3, %2, %1, %0|%0, %1, %2, %3}
9747    pmacssdql\t{%3, %2, %1, %0|%0, %1, %2, %3}
9748    pmacssdql\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9749   [(set_attr "type" "ssemuladd")
9750    (set_attr "mode" "TI")])
9751
9752 (define_insn "sse5_pmacssdqh"
9753   [(set (match_operand:V2DI 0 "register_operand" "=x,x,x")
9754         (ss_plus:V2DI
9755          (mult:V2DI
9756           (sign_extend:V2DI
9757            (vec_select:V2SI
9758             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9759             (parallel [(const_int 0)
9760                        (const_int 2)])))
9761           (sign_extend:V2DI
9762            (vec_select:V2SI
9763             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9764             (parallel [(const_int 0)
9765                        (const_int 2)]))))
9766          (match_operand:V2DI 3 "register_operand" "0,0,0")))]
9767   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9768   "@
9769    pmacssdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}
9770    pmacssdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}
9771    pmacssdqh\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9772   [(set_attr "type" "ssemuladd")
9773    (set_attr "mode" "TI")])
9774
9775 (define_insn "sse5_pmacsdql"
9776   [(set (match_operand:V2DI 0 "register_operand" "=x,x,x")
9777         (plus:V2DI
9778          (mult:V2DI
9779           (sign_extend:V2DI
9780            (vec_select:V2SI
9781             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9782             (parallel [(const_int 1)
9783                        (const_int 3)])))
9784           (sign_extend:V2DI
9785            (vec_select:V2SI
9786             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9787             (parallel [(const_int 1)
9788                        (const_int 3)]))))
9789          (match_operand:V2DI 3 "register_operand" "0,0,0")))]
9790   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9791   "@
9792    pmacsdql\t{%3, %2, %1, %0|%0, %1, %2, %3}
9793    pmacsdql\t{%3, %2, %1, %0|%0, %1, %2, %3}
9794    pmacsdql\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9795   [(set_attr "type" "ssemuladd")
9796    (set_attr "mode" "TI")])
9797
9798 (define_insn_and_split "*sse5_pmacsdql_mem"
9799   [(set (match_operand:V2DI 0 "register_operand" "=&x,&x,&x")
9800         (plus:V2DI
9801          (mult:V2DI
9802           (sign_extend:V2DI
9803            (vec_select:V2SI
9804             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9805             (parallel [(const_int 1)
9806                        (const_int 3)])))
9807           (sign_extend:V2DI
9808            (vec_select:V2SI
9809             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9810             (parallel [(const_int 1)
9811                        (const_int 3)]))))
9812          (match_operand:V2DI 3 "memory_operand" "m,m,m")))]
9813   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, -1, true)"
9814   "#"
9815   "&& (reload_completed
9816        || (!reg_mentioned_p (operands[0], operands[1])
9817            && !reg_mentioned_p (operands[0], operands[2])))"
9818   [(set (match_dup 0)
9819         (match_dup 3))
9820    (set (match_dup 0)
9821         (plus:V2DI
9822          (mult:V2DI
9823           (sign_extend:V2DI
9824            (vec_select:V2SI
9825             (match_dup 1)
9826             (parallel [(const_int 1)
9827                        (const_int 3)])))
9828           (sign_extend:V2DI
9829            (vec_select:V2SI
9830             (match_dup 2)
9831             (parallel [(const_int 1)
9832                        (const_int 3)]))))
9833          (match_dup 0)))])
9834
9835 ;; We don't have a straight 32-bit parallel multiply and extend on SSE5, so
9836 ;; fake it with a multiply/add.  In general, we expect the define_split to
9837 ;; occur before register allocation, so we have to handle the corner case where
9838 ;; the target is the same as operands 1/2
9839 (define_insn_and_split "sse5_mulv2div2di3_low"
9840   [(set (match_operand:V2DI 0 "register_operand" "=&x")
9841         (mult:V2DI
9842           (sign_extend:V2DI
9843             (vec_select:V2SI
9844               (match_operand:V4SI 1 "nonimmediate_operand" "%x")
9845               (parallel [(const_int 1)
9846                          (const_int 3)])))
9847           (sign_extend:V2DI
9848             (vec_select:V2SI
9849               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
9850               (parallel [(const_int 1)
9851                          (const_int 3)])))))]
9852   "TARGET_SSE5"
9853   "#"
9854   "&& (reload_completed
9855        || (!reg_mentioned_p (operands[0], operands[1])
9856            && !reg_mentioned_p (operands[0], operands[2])))"
9857   [(set (match_dup 0)
9858         (match_dup 3))
9859    (set (match_dup 0)
9860         (plus:V2DI
9861          (mult:V2DI
9862           (sign_extend:V2DI
9863            (vec_select:V2SI
9864             (match_dup 1)
9865             (parallel [(const_int 1)
9866                        (const_int 3)])))
9867           (sign_extend:V2DI
9868            (vec_select:V2SI
9869             (match_dup 2)
9870             (parallel [(const_int 1)
9871                        (const_int 3)]))))
9872          (match_dup 0)))]
9873 {
9874   operands[3] = CONST0_RTX (V2DImode);
9875 }
9876   [(set_attr "type" "ssemuladd")
9877    (set_attr "mode" "TI")])
9878
9879 (define_insn "sse5_pmacsdqh"
9880   [(set (match_operand:V2DI 0 "register_operand" "=x,x,x")
9881         (plus:V2DI
9882          (mult:V2DI
9883           (sign_extend:V2DI
9884            (vec_select:V2SI
9885             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9886             (parallel [(const_int 0)
9887                        (const_int 2)])))
9888           (sign_extend:V2DI
9889            (vec_select:V2SI
9890             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9891             (parallel [(const_int 0)
9892                        (const_int 2)]))))
9893          (match_operand:V2DI 3 "register_operand" "0,0,0")))]
9894   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
9895   "@
9896    pmacsdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}
9897    pmacsdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}
9898    pmacsdqh\t{%3, %1, %2, %0|%0, %2, %1, %3}"
9899   [(set_attr "type" "ssemuladd")
9900    (set_attr "mode" "TI")])
9901
9902 (define_insn_and_split "*sse5_pmacsdqh_mem"
9903   [(set (match_operand:V2DI 0 "register_operand" "=&x,&x,&x")
9904         (plus:V2DI
9905          (mult:V2DI
9906           (sign_extend:V2DI
9907            (vec_select:V2SI
9908             (match_operand:V4SI 1 "nonimmediate_operand" "%x,x,m")
9909             (parallel [(const_int 0)
9910                        (const_int 2)])))
9911           (sign_extend:V2DI
9912            (vec_select:V2SI
9913             (match_operand:V4SI 2 "nonimmediate_operand" "x,m,x")
9914             (parallel [(const_int 0)
9915                        (const_int 2)]))))
9916          (match_operand:V2DI 3 "memory_operand" "m,m,m")))]
9917   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, -1, true)"
9918   "#"
9919   "&& (reload_completed
9920        || (!reg_mentioned_p (operands[0], operands[1])
9921            && !reg_mentioned_p (operands[0], operands[2])))"
9922   [(set (match_dup 0)
9923         (match_dup 3))
9924    (set (match_dup 0)
9925         (plus:V2DI
9926          (mult:V2DI
9927           (sign_extend:V2DI
9928            (vec_select:V2SI
9929             (match_dup 1)
9930             (parallel [(const_int 0)
9931                        (const_int 2)])))
9932           (sign_extend:V2DI
9933            (vec_select:V2SI
9934             (match_dup 2)
9935             (parallel [(const_int 0)
9936                        (const_int 2)]))))
9937          (match_dup 0)))])
9938
9939 ;; We don't have a straight 32-bit parallel multiply and extend on SSE5, so
9940 ;; fake it with a multiply/add.  In general, we expect the define_split to
9941 ;; occur before register allocation, so we have to handle the corner case where
9942 ;; the target is the same as either operands[1] or operands[2]
9943 (define_insn_and_split "sse5_mulv2div2di3_high"
9944   [(set (match_operand:V2DI 0 "register_operand" "=&x")
9945         (mult:V2DI
9946           (sign_extend:V2DI
9947             (vec_select:V2SI
9948               (match_operand:V4SI 1 "nonimmediate_operand" "%x")
9949               (parallel [(const_int 0)
9950                          (const_int 2)])))
9951           (sign_extend:V2DI
9952             (vec_select:V2SI
9953               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
9954               (parallel [(const_int 0)
9955                          (const_int 2)])))))]
9956   "TARGET_SSE5"
9957   "#"
9958   "&& (reload_completed
9959        || (!reg_mentioned_p (operands[0], operands[1])
9960            && !reg_mentioned_p (operands[0], operands[2])))"
9961   [(set (match_dup 0)
9962         (match_dup 3))
9963    (set (match_dup 0)
9964         (plus:V2DI
9965          (mult:V2DI
9966           (sign_extend:V2DI
9967            (vec_select:V2SI
9968             (match_dup 1)
9969             (parallel [(const_int 0)
9970                        (const_int 2)])))
9971           (sign_extend:V2DI
9972            (vec_select:V2SI
9973             (match_dup 2)
9974             (parallel [(const_int 0)
9975                        (const_int 2)]))))
9976          (match_dup 0)))]
9977 {
9978   operands[3] = CONST0_RTX (V2DImode);
9979 }
9980   [(set_attr "type" "ssemuladd")
9981    (set_attr "mode" "TI")])
9982
9983 ;; SSE5 parallel integer multiply/add instructions for the intrinisics
9984 (define_insn "sse5_pmacsswd"
9985   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
9986         (ss_plus:V4SI
9987          (mult:V4SI
9988           (sign_extend:V4SI
9989            (vec_select:V4HI
9990             (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,m")
9991             (parallel [(const_int 1)
9992                        (const_int 3)
9993                        (const_int 5)
9994                        (const_int 7)])))
9995           (sign_extend:V4SI
9996            (vec_select:V4HI
9997             (match_operand:V8HI 2 "nonimmediate_operand" "x,m,x")
9998             (parallel [(const_int 1)
9999                        (const_int 3)
10000                        (const_int 5)
10001                        (const_int 7)]))))
10002          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
10003   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
10004   "@
10005    pmacsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10006    pmacsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10007    pmacsswd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
10008   [(set_attr "type" "ssemuladd")
10009    (set_attr "mode" "TI")])
10010
10011 (define_insn "sse5_pmacswd"
10012   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
10013         (plus:V4SI
10014          (mult:V4SI
10015           (sign_extend:V4SI
10016            (vec_select:V4HI
10017             (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,m")
10018             (parallel [(const_int 1)
10019                        (const_int 3)
10020                        (const_int 5)
10021                        (const_int 7)])))
10022           (sign_extend:V4SI
10023            (vec_select:V4HI
10024             (match_operand:V8HI 2 "nonimmediate_operand" "x,m,x")
10025             (parallel [(const_int 1)
10026                        (const_int 3)
10027                        (const_int 5)
10028                        (const_int 7)]))))
10029          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
10030   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
10031   "@
10032    pmacswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10033    pmacswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10034    pmacswd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
10035   [(set_attr "type" "ssemuladd")
10036    (set_attr "mode" "TI")])
10037
10038 (define_insn "sse5_pmadcsswd"
10039   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
10040         (ss_plus:V4SI
10041          (plus:V4SI
10042           (mult:V4SI
10043            (sign_extend:V4SI
10044             (vec_select:V4HI
10045              (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,m")
10046              (parallel [(const_int 0)
10047                         (const_int 2)
10048                         (const_int 4)
10049                         (const_int 6)])))
10050            (sign_extend:V4SI
10051             (vec_select:V4HI
10052              (match_operand:V8HI 2 "nonimmediate_operand" "x,m,x")
10053              (parallel [(const_int 0)
10054                         (const_int 2)
10055                         (const_int 4)
10056                         (const_int 6)]))))
10057           (mult:V4SI
10058            (sign_extend:V4SI
10059             (vec_select:V4HI
10060              (match_dup 1)
10061              (parallel [(const_int 1)
10062                         (const_int 3)
10063                         (const_int 5)
10064                         (const_int 7)])))
10065            (sign_extend:V4SI
10066             (vec_select:V4HI
10067              (match_dup 2)
10068              (parallel [(const_int 1)
10069                         (const_int 3)
10070                         (const_int 5)
10071                         (const_int 7)])))))
10072          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
10073   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
10074   "@
10075    pmadcsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10076    pmadcsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10077    pmadcsswd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
10078   [(set_attr "type" "ssemuladd")
10079    (set_attr "mode" "TI")])
10080
10081 (define_insn "sse5_pmadcswd"
10082   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x")
10083         (plus:V4SI
10084          (plus:V4SI
10085           (mult:V4SI
10086            (sign_extend:V4SI
10087             (vec_select:V4HI
10088              (match_operand:V8HI 1 "nonimmediate_operand" "%x,x,m")
10089              (parallel [(const_int 0)
10090                         (const_int 2)
10091                         (const_int 4)
10092                         (const_int 6)])))
10093            (sign_extend:V4SI
10094             (vec_select:V4HI
10095              (match_operand:V8HI 2 "nonimmediate_operand" "x,m,x")
10096              (parallel [(const_int 0)
10097                         (const_int 2)
10098                         (const_int 4)
10099                         (const_int 6)]))))
10100           (mult:V4SI
10101            (sign_extend:V4SI
10102             (vec_select:V4HI
10103              (match_dup 1)
10104              (parallel [(const_int 1)
10105                         (const_int 3)
10106                         (const_int 5)
10107                         (const_int 7)])))
10108            (sign_extend:V4SI
10109             (vec_select:V4HI
10110              (match_dup 2)
10111              (parallel [(const_int 1)
10112                         (const_int 3)
10113                         (const_int 5)
10114                         (const_int 7)])))))
10115          (match_operand:V4SI 3 "register_operand" "0,0,0")))]
10116   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, false, 1, true)"
10117   "@
10118    pmadcswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10119    pmadcswd\t{%3, %2, %1, %0|%0, %1, %2, %3}
10120    pmadcswd\t{%3, %1, %2, %0|%0, %2, %1, %3}"
10121   [(set_attr "type" "ssemuladd")
10122    (set_attr "mode" "TI")])
10123
10124 ;; SSE5 parallel XMM conditional moves
10125 (define_insn "sse5_pcmov_<mode>"
10126   [(set (match_operand:SSEMODE 0 "register_operand" "=x,x,x,x")
10127         (if_then_else:SSEMODE
10128           (match_operand:SSEMODE 3 "nonimmediate_operand" "0,0,xm,x")
10129           (match_operand:SSEMODE 1 "vector_move_operand" "x,xm,0,0")
10130           (match_operand:SSEMODE 2 "vector_move_operand" "xm,x,x,xm")))]
10131   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10132   "@
10133    pcmov\t{%3, %2, %1, %0|%0, %1, %2, %3}
10134    pcmov\t{%3, %2, %1, %0|%0, %1, %2, %3}
10135    pcmov\t{%3, %2, %1, %0|%0, %1, %2, %3}
10136    pcmov\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10137   [(set_attr "type" "sse4arg")])
10138
10139 ;; SSE5 horizontal add/subtract instructions
10140 (define_insn "sse5_phaddbw"
10141   [(set (match_operand:V8HI 0 "register_operand" "=x")
10142         (plus:V8HI
10143          (sign_extend:V8HI
10144           (vec_select:V8QI
10145            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10146            (parallel [(const_int 0)
10147                       (const_int 2)
10148                       (const_int 4)
10149                       (const_int 6)
10150                       (const_int 8)
10151                       (const_int 10)
10152                       (const_int 12)
10153                       (const_int 14)])))
10154          (sign_extend:V8HI
10155           (vec_select:V8QI
10156            (match_dup 1)
10157            (parallel [(const_int 1)
10158                       (const_int 3)
10159                       (const_int 5)
10160                       (const_int 7)
10161                       (const_int 9)
10162                       (const_int 11)
10163                       (const_int 13)
10164                       (const_int 15)])))))]
10165   "TARGET_SSE5"
10166   "phaddbw\t{%1, %0|%0, %1}"
10167   [(set_attr "type" "sseiadd1")])
10168
10169 (define_insn "sse5_phaddbd"
10170   [(set (match_operand:V4SI 0 "register_operand" "=x")
10171         (plus:V4SI
10172          (plus:V4SI
10173           (sign_extend:V4SI
10174            (vec_select:V4QI
10175             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10176             (parallel [(const_int 0)
10177                        (const_int 4)
10178                        (const_int 8)
10179                        (const_int 12)])))
10180           (sign_extend:V4SI
10181            (vec_select:V4QI
10182             (match_dup 1)
10183             (parallel [(const_int 1)
10184                        (const_int 5)
10185                        (const_int 9)
10186                        (const_int 13)]))))
10187          (plus:V4SI
10188           (sign_extend:V4SI
10189            (vec_select:V4QI
10190             (match_dup 1)
10191             (parallel [(const_int 2)
10192                        (const_int 6)
10193                        (const_int 10)
10194                        (const_int 14)])))
10195           (sign_extend:V4SI
10196            (vec_select:V4QI
10197             (match_dup 1)
10198             (parallel [(const_int 3)
10199                        (const_int 7)
10200                        (const_int 11)
10201                        (const_int 15)]))))))]
10202   "TARGET_SSE5"
10203   "phaddbd\t{%1, %0|%0, %1}"
10204   [(set_attr "type" "sseiadd1")])
10205
10206 (define_insn "sse5_phaddbq"
10207   [(set (match_operand:V2DI 0 "register_operand" "=x")
10208         (plus:V2DI
10209          (plus:V2DI
10210           (plus:V2DI
10211            (sign_extend:V2DI
10212             (vec_select:V2QI
10213              (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10214              (parallel [(const_int 0)
10215                         (const_int 4)])))
10216            (sign_extend:V2DI
10217             (vec_select:V2QI
10218              (match_dup 1)
10219              (parallel [(const_int 1)
10220                         (const_int 5)]))))
10221           (plus:V2DI
10222            (sign_extend:V2DI
10223             (vec_select:V2QI
10224              (match_dup 1)
10225              (parallel [(const_int 2)
10226                         (const_int 6)])))
10227            (sign_extend:V2DI
10228             (vec_select:V2QI
10229              (match_dup 1)
10230              (parallel [(const_int 3)
10231                         (const_int 7)])))))
10232          (plus:V2DI
10233           (plus:V2DI
10234            (sign_extend:V2DI
10235             (vec_select:V2QI
10236              (match_dup 1)
10237              (parallel [(const_int 8)
10238                         (const_int 12)])))
10239            (sign_extend:V2DI
10240             (vec_select:V2QI
10241              (match_dup 1)
10242              (parallel [(const_int 9)
10243                         (const_int 13)]))))
10244           (plus:V2DI
10245            (sign_extend:V2DI
10246             (vec_select:V2QI
10247              (match_dup 1)
10248              (parallel [(const_int 10)
10249                         (const_int 14)])))
10250            (sign_extend:V2DI
10251             (vec_select:V2QI
10252              (match_dup 1)
10253              (parallel [(const_int 11)
10254                         (const_int 15)])))))))]
10255   "TARGET_SSE5"
10256   "phaddbq\t{%1, %0|%0, %1}"
10257   [(set_attr "type" "sseiadd1")])
10258
10259 (define_insn "sse5_phaddwd"
10260   [(set (match_operand:V4SI 0 "register_operand" "=x")
10261         (plus:V4SI
10262          (sign_extend:V4SI
10263           (vec_select:V4HI
10264            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10265            (parallel [(const_int 0)
10266                       (const_int 2)
10267                       (const_int 4)
10268                       (const_int 6)])))
10269          (sign_extend:V4SI
10270           (vec_select:V4HI
10271            (match_dup 1)
10272            (parallel [(const_int 1)
10273                       (const_int 3)
10274                       (const_int 5)
10275                       (const_int 7)])))))]
10276   "TARGET_SSE5"
10277   "phaddwd\t{%1, %0|%0, %1}"
10278   [(set_attr "type" "sseiadd1")])
10279
10280 (define_insn "sse5_phaddwq"
10281   [(set (match_operand:V2DI 0 "register_operand" "=x")
10282         (plus:V2DI
10283          (plus:V2DI
10284           (sign_extend:V2DI
10285            (vec_select:V2HI
10286             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10287             (parallel [(const_int 0)
10288                        (const_int 4)])))
10289           (sign_extend:V2DI
10290            (vec_select:V2HI
10291             (match_dup 1)
10292             (parallel [(const_int 1)
10293                        (const_int 5)]))))
10294          (plus:V2DI
10295           (sign_extend:V2DI
10296            (vec_select:V2HI
10297             (match_dup 1)
10298             (parallel [(const_int 2)
10299                        (const_int 6)])))
10300           (sign_extend:V2DI
10301            (vec_select:V2HI
10302             (match_dup 1)
10303             (parallel [(const_int 3)
10304                        (const_int 7)]))))))]
10305   "TARGET_SSE5"
10306   "phaddwq\t{%1, %0|%0, %1}"
10307   [(set_attr "type" "sseiadd1")])
10308
10309 (define_insn "sse5_phadddq"
10310   [(set (match_operand:V2DI 0 "register_operand" "=x")
10311         (plus:V2DI
10312          (sign_extend:V2DI
10313           (vec_select:V2SI
10314            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10315            (parallel [(const_int 0)
10316                       (const_int 2)])))
10317          (sign_extend:V2DI
10318           (vec_select:V2SI
10319            (match_dup 1)
10320            (parallel [(const_int 1)
10321                       (const_int 3)])))))]
10322   "TARGET_SSE5"
10323   "phadddq\t{%1, %0|%0, %1}"
10324   [(set_attr "type" "sseiadd1")])
10325
10326 (define_insn "sse5_phaddubw"
10327   [(set (match_operand:V8HI 0 "register_operand" "=x")
10328         (plus:V8HI
10329          (zero_extend:V8HI
10330           (vec_select:V8QI
10331            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10332            (parallel [(const_int 0)
10333                       (const_int 2)
10334                       (const_int 4)
10335                       (const_int 6)
10336                       (const_int 8)
10337                       (const_int 10)
10338                       (const_int 12)
10339                       (const_int 14)])))
10340          (zero_extend:V8HI
10341           (vec_select:V8QI
10342            (match_dup 1)
10343            (parallel [(const_int 1)
10344                       (const_int 3)
10345                       (const_int 5)
10346                       (const_int 7)
10347                       (const_int 9)
10348                       (const_int 11)
10349                       (const_int 13)
10350                       (const_int 15)])))))]
10351   "TARGET_SSE5"
10352   "phaddubw\t{%1, %0|%0, %1}"
10353   [(set_attr "type" "sseiadd1")])
10354
10355 (define_insn "sse5_phaddubd"
10356   [(set (match_operand:V4SI 0 "register_operand" "=x")
10357         (plus:V4SI
10358          (plus:V4SI
10359           (zero_extend:V4SI
10360            (vec_select:V4QI
10361             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10362             (parallel [(const_int 0)
10363                        (const_int 4)
10364                        (const_int 8)
10365                        (const_int 12)])))
10366           (zero_extend:V4SI
10367            (vec_select:V4QI
10368             (match_dup 1)
10369             (parallel [(const_int 1)
10370                        (const_int 5)
10371                        (const_int 9)
10372                        (const_int 13)]))))
10373          (plus:V4SI
10374           (zero_extend:V4SI
10375            (vec_select:V4QI
10376             (match_dup 1)
10377             (parallel [(const_int 2)
10378                        (const_int 6)
10379                        (const_int 10)
10380                        (const_int 14)])))
10381           (zero_extend:V4SI
10382            (vec_select:V4QI
10383             (match_dup 1)
10384             (parallel [(const_int 3)
10385                        (const_int 7)
10386                        (const_int 11)
10387                        (const_int 15)]))))))]
10388   "TARGET_SSE5"
10389   "phaddubd\t{%1, %0|%0, %1}"
10390   [(set_attr "type" "sseiadd1")])
10391
10392 (define_insn "sse5_phaddubq"
10393   [(set (match_operand:V2DI 0 "register_operand" "=x")
10394         (plus:V2DI
10395          (plus:V2DI
10396           (plus:V2DI
10397            (zero_extend:V2DI
10398             (vec_select:V2QI
10399              (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10400              (parallel [(const_int 0)
10401                         (const_int 4)])))
10402            (sign_extend:V2DI
10403             (vec_select:V2QI
10404              (match_dup 1)
10405              (parallel [(const_int 1)
10406                         (const_int 5)]))))
10407           (plus:V2DI
10408            (zero_extend:V2DI
10409             (vec_select:V2QI
10410              (match_dup 1)
10411              (parallel [(const_int 2)
10412                         (const_int 6)])))
10413            (zero_extend:V2DI
10414             (vec_select:V2QI
10415              (match_dup 1)
10416              (parallel [(const_int 3)
10417                         (const_int 7)])))))
10418          (plus:V2DI
10419           (plus:V2DI
10420            (zero_extend:V2DI
10421             (vec_select:V2QI
10422              (match_dup 1)
10423              (parallel [(const_int 8)
10424                         (const_int 12)])))
10425            (sign_extend:V2DI
10426             (vec_select:V2QI
10427              (match_dup 1)
10428              (parallel [(const_int 9)
10429                         (const_int 13)]))))
10430           (plus:V2DI
10431            (zero_extend:V2DI
10432             (vec_select:V2QI
10433              (match_dup 1)
10434              (parallel [(const_int 10)
10435                         (const_int 14)])))
10436            (zero_extend:V2DI
10437             (vec_select:V2QI
10438              (match_dup 1)
10439              (parallel [(const_int 11)
10440                         (const_int 15)])))))))]
10441   "TARGET_SSE5"
10442   "phaddubq\t{%1, %0|%0, %1}"
10443   [(set_attr "type" "sseiadd1")])
10444
10445 (define_insn "sse5_phadduwd"
10446   [(set (match_operand:V4SI 0 "register_operand" "=x")
10447         (plus:V4SI
10448          (zero_extend:V4SI
10449           (vec_select:V4HI
10450            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10451            (parallel [(const_int 0)
10452                       (const_int 2)
10453                       (const_int 4)
10454                       (const_int 6)])))
10455          (zero_extend:V4SI
10456           (vec_select:V4HI
10457            (match_dup 1)
10458            (parallel [(const_int 1)
10459                       (const_int 3)
10460                       (const_int 5)
10461                       (const_int 7)])))))]
10462   "TARGET_SSE5"
10463   "phadduwd\t{%1, %0|%0, %1}"
10464   [(set_attr "type" "sseiadd1")])
10465
10466 (define_insn "sse5_phadduwq"
10467   [(set (match_operand:V2DI 0 "register_operand" "=x")
10468         (plus:V2DI
10469          (plus:V2DI
10470           (zero_extend:V2DI
10471            (vec_select:V2HI
10472             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10473             (parallel [(const_int 0)
10474                        (const_int 4)])))
10475           (zero_extend:V2DI
10476            (vec_select:V2HI
10477             (match_dup 1)
10478             (parallel [(const_int 1)
10479                        (const_int 5)]))))
10480          (plus:V2DI
10481           (zero_extend:V2DI
10482            (vec_select:V2HI
10483             (match_dup 1)
10484             (parallel [(const_int 2)
10485                        (const_int 6)])))
10486           (zero_extend:V2DI
10487            (vec_select:V2HI
10488             (match_dup 1)
10489             (parallel [(const_int 3)
10490                        (const_int 7)]))))))]
10491   "TARGET_SSE5"
10492   "phadduwq\t{%1, %0|%0, %1}"
10493   [(set_attr "type" "sseiadd1")])
10494
10495 (define_insn "sse5_phaddudq"
10496   [(set (match_operand:V2DI 0 "register_operand" "=x")
10497         (plus:V2DI
10498          (zero_extend:V2DI
10499           (vec_select:V2SI
10500            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10501            (parallel [(const_int 0)
10502                       (const_int 2)])))
10503          (zero_extend:V2DI
10504           (vec_select:V2SI
10505            (match_dup 1)
10506            (parallel [(const_int 1)
10507                       (const_int 3)])))))]
10508   "TARGET_SSE5"
10509   "phaddudq\t{%1, %0|%0, %1}"
10510   [(set_attr "type" "sseiadd1")])
10511
10512 (define_insn "sse5_phsubbw"
10513   [(set (match_operand:V8HI 0 "register_operand" "=x")
10514         (minus:V8HI
10515          (sign_extend:V8HI
10516           (vec_select:V8QI
10517            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10518            (parallel [(const_int 0)
10519                       (const_int 2)
10520                       (const_int 4)
10521                       (const_int 6)
10522                       (const_int 8)
10523                       (const_int 10)
10524                       (const_int 12)
10525                       (const_int 14)])))
10526          (sign_extend:V8HI
10527           (vec_select:V8QI
10528            (match_dup 1)
10529            (parallel [(const_int 1)
10530                       (const_int 3)
10531                       (const_int 5)
10532                       (const_int 7)
10533                       (const_int 9)
10534                       (const_int 11)
10535                       (const_int 13)
10536                       (const_int 15)])))))]
10537   "TARGET_SSE5"
10538   "phsubbw\t{%1, %0|%0, %1}"
10539   [(set_attr "type" "sseiadd1")])
10540
10541 (define_insn "sse5_phsubwd"
10542   [(set (match_operand:V4SI 0 "register_operand" "=x")
10543         (minus:V4SI
10544          (sign_extend:V4SI
10545           (vec_select:V4HI
10546            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10547            (parallel [(const_int 0)
10548                       (const_int 2)
10549                       (const_int 4)
10550                       (const_int 6)])))
10551          (sign_extend:V4SI
10552           (vec_select:V4HI
10553            (match_dup 1)
10554            (parallel [(const_int 1)
10555                       (const_int 3)
10556                       (const_int 5)
10557                       (const_int 7)])))))]
10558   "TARGET_SSE5"
10559   "phsubwd\t{%1, %0|%0, %1}"
10560   [(set_attr "type" "sseiadd1")])
10561
10562 (define_insn "sse5_phsubdq"
10563   [(set (match_operand:V2DI 0 "register_operand" "=x")
10564         (minus:V2DI
10565          (sign_extend:V2DI
10566           (vec_select:V2SI
10567            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10568            (parallel [(const_int 0)
10569                       (const_int 2)])))
10570          (sign_extend:V2DI
10571           (vec_select:V2SI
10572            (match_dup 1)
10573            (parallel [(const_int 1)
10574                       (const_int 3)])))))]
10575   "TARGET_SSE5"
10576   "phsubdq\t{%1, %0|%0, %1}"
10577   [(set_attr "type" "sseiadd1")])
10578
10579 ;; SSE5 permute instructions
10580 (define_insn "sse5_pperm"
10581   [(set (match_operand:V16QI 0 "register_operand" "=x,x,x,x")
10582         (unspec:V16QI
10583           [(match_operand:V16QI 1 "nonimmediate_operand" "0,0,x,xm")
10584            (match_operand:V16QI 2 "nonimmediate_operand" "x,xm,xm,x")
10585            (match_operand:V16QI 3 "nonimmediate_operand" "xm,x,0,0")]
10586           UNSPEC_SSE5_PERMUTE))]
10587   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10588   "pperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10589   [(set_attr "type" "sse4arg")
10590    (set_attr "mode" "TI")])
10591
10592 ;; The following are for the various unpack insns which doesn't need the first
10593 ;; source operand, so we can just use the output operand for the first operand.
10594 ;; This allows either of the other two operands to be a memory operand.  We
10595 ;; can't just use the first operand as an argument to the normal pperm because
10596 ;; then an output only argument, suddenly becomes an input operand.
10597 (define_insn "sse5_pperm_zero_v16qi_v8hi"
10598   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
10599         (zero_extend:V8HI
10600          (vec_select:V8QI
10601           (match_operand:V16QI 1 "nonimmediate_operand" "xm,x")
10602           (match_operand 2 "" ""))))    ;; parallel with const_int's
10603    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10604   "TARGET_SSE5
10605    && (register_operand (operands[1], V16QImode)
10606        || register_operand (operands[2], V16QImode))"
10607   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10608   [(set_attr "type" "sseadd")
10609    (set_attr "mode" "TI")])
10610
10611 (define_insn "sse5_pperm_sign_v16qi_v8hi"
10612   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
10613         (sign_extend:V8HI
10614          (vec_select:V8QI
10615           (match_operand:V16QI 1 "nonimmediate_operand" "xm,x")
10616           (match_operand 2 "" ""))))    ;; parallel with const_int's
10617    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10618   "TARGET_SSE5
10619    && (register_operand (operands[1], V16QImode)
10620        || register_operand (operands[2], V16QImode))"
10621   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10622   [(set_attr "type" "sseadd")
10623    (set_attr "mode" "TI")])
10624
10625 (define_insn "sse5_pperm_zero_v8hi_v4si"
10626   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
10627         (zero_extend:V4SI
10628          (vec_select:V4HI
10629           (match_operand:V8HI 1 "nonimmediate_operand" "xm,x")
10630           (match_operand 2 "" ""))))    ;; parallel with const_int's
10631    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10632   "TARGET_SSE5
10633    && (register_operand (operands[1], V8HImode)
10634        || register_operand (operands[2], V16QImode))"
10635   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10636   [(set_attr "type" "sseadd")
10637    (set_attr "mode" "TI")])
10638
10639 (define_insn "sse5_pperm_sign_v8hi_v4si"
10640   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
10641         (sign_extend:V4SI
10642          (vec_select:V4HI
10643           (match_operand:V8HI 1 "nonimmediate_operand" "xm,x")
10644           (match_operand 2 "" ""))))    ;; parallel with const_int's
10645    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10646   "TARGET_SSE5
10647    && (register_operand (operands[1], V8HImode)
10648        || register_operand (operands[2], V16QImode))"
10649   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10650   [(set_attr "type" "sseadd")
10651    (set_attr "mode" "TI")])
10652
10653 (define_insn "sse5_pperm_zero_v4si_v2di"
10654   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
10655         (zero_extend:V2DI
10656          (vec_select:V2SI
10657           (match_operand:V4SI 1 "nonimmediate_operand" "xm,x")
10658           (match_operand 2 "" ""))))    ;; parallel with const_int's
10659    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10660   "TARGET_SSE5
10661    && (register_operand (operands[1], V4SImode)
10662        || register_operand (operands[2], V16QImode))"
10663   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10664   [(set_attr "type" "sseadd")
10665    (set_attr "mode" "TI")])
10666
10667 (define_insn "sse5_pperm_sign_v4si_v2di"
10668   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
10669         (sign_extend:V2DI
10670          (vec_select:V2SI
10671           (match_operand:V4SI 1 "nonimmediate_operand" "xm,x")
10672           (match_operand 2 "" ""))))    ;; parallel with const_int's
10673    (use (match_operand:V16QI 3 "nonimmediate_operand" "x,xm"))]
10674   "TARGET_SSE5
10675    && (register_operand (operands[1], V4SImode)
10676        || register_operand (operands[2], V16QImode))"
10677   "pperm\t{%3, %1, %0, %0|%0, %0, %1, %3}"
10678   [(set_attr "type" "sseadd")
10679    (set_attr "mode" "TI")])
10680
10681 ;; SSE5 pack instructions that combine two vectors into a smaller vector
10682 (define_insn "sse5_pperm_pack_v2di_v4si"
10683   [(set (match_operand:V4SI 0 "register_operand" "=x,x,x,x")
10684         (vec_concat:V4SI
10685          (truncate:V2SI
10686           (match_operand:V2DI 1 "nonimmediate_operand" "0,0,x,xm"))
10687          (truncate:V2SI
10688           (match_operand:V2DI 2 "nonimmediate_operand" "x,xm,xm,x"))))
10689    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x,0,0"))]
10690   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10691   "pperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10692   [(set_attr "type" "sse4arg")
10693    (set_attr "mode" "TI")])
10694
10695 (define_insn "sse5_pperm_pack_v4si_v8hi"
10696   [(set (match_operand:V8HI 0 "register_operand" "=x,x,x,x")
10697         (vec_concat:V8HI
10698          (truncate:V4HI
10699           (match_operand:V4SI 1 "nonimmediate_operand" "0,0,x,xm"))
10700          (truncate:V4HI
10701           (match_operand:V4SI 2 "nonimmediate_operand" "x,xm,xm,x"))))
10702    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x,0,0"))]
10703   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10704   "pperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10705   [(set_attr "type" "sse4arg")
10706    (set_attr "mode" "TI")])
10707
10708 (define_insn "sse5_pperm_pack_v8hi_v16qi"
10709   [(set (match_operand:V16QI 0 "register_operand" "=x,x,x,x")
10710         (vec_concat:V16QI
10711          (truncate:V8QI
10712           (match_operand:V8HI 1 "nonimmediate_operand" "0,0,x,xm"))
10713          (truncate:V8QI
10714           (match_operand:V8HI 2 "nonimmediate_operand" "x,xm,xm,x"))))
10715    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x,0,0"))]
10716   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10717   "pperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10718   [(set_attr "type" "sse4arg")
10719    (set_attr "mode" "TI")])
10720
10721 ;; Floating point permutation (permps, permpd)
10722 (define_insn "sse5_perm<mode>"
10723   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x,x,x,x")
10724         (unspec:SSEMODEF2P
10725          [(match_operand:SSEMODEF2P 1 "nonimmediate_operand" "0,0,x,xm")
10726           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "x,xm,xm,x")
10727           (match_operand:V16QI 3 "nonimmediate_operand" "xm,x,0,0")]
10728          UNSPEC_SSE5_PERMUTE))]
10729   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
10730   "perm<ssemodesuffixf4>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10731   [(set_attr "type" "sse4arg")
10732    (set_attr "mode" "<MODE>")])
10733
10734 ;; SSE5 packed rotate instructions
10735 (define_expand "rotl<mode>3"
10736   [(set (match_operand:SSEMODE1248 0 "register_operand" "")
10737         (rotate:SSEMODE1248
10738          (match_operand:SSEMODE1248 1 "nonimmediate_operand" "")
10739          (match_operand:SI 2 "general_operand")))]
10740   "TARGET_SSE5"
10741 {
10742   /* If we were given a scalar, convert it to parallel */
10743   if (! const_0_to_<sserotatemax>_operand (operands[2], SImode))
10744     {
10745       rtvec vs = rtvec_alloc (<ssescalarnum>);
10746       rtx par = gen_rtx_PARALLEL (<MODE>mode, vs);
10747       rtx reg = gen_reg_rtx (<MODE>mode);
10748       rtx op2 = operands[2];
10749       int i;
10750
10751       if (GET_MODE (op2) != <ssescalarmode>mode)
10752         {
10753           op2 = gen_reg_rtx (<ssescalarmode>mode);
10754           convert_move (op2, operands[2], false);
10755         }
10756
10757       for (i = 0; i < <ssescalarnum>; i++)
10758         RTVEC_ELT (vs, i) = op2;
10759
10760       emit_insn (gen_vec_init<mode> (reg, par));
10761       emit_insn (gen_sse5_vrotl<mode>3 (operands[0], operands[1], reg));
10762       DONE;
10763     }
10764 })
10765
10766 (define_expand "rotr<mode>3"
10767   [(set (match_operand:SSEMODE1248 0 "register_operand" "")
10768         (rotatert:SSEMODE1248
10769          (match_operand:SSEMODE1248 1 "nonimmediate_operand" "")
10770          (match_operand:SI 2 "general_operand")))]
10771   "TARGET_SSE5"
10772 {
10773   /* If we were given a scalar, convert it to parallel */
10774   if (! const_0_to_<sserotatemax>_operand (operands[2], SImode))
10775     {
10776       rtvec vs = rtvec_alloc (<ssescalarnum>);
10777       rtx par = gen_rtx_PARALLEL (<MODE>mode, vs);
10778       rtx neg = gen_reg_rtx (<MODE>mode);
10779       rtx reg = gen_reg_rtx (<MODE>mode);
10780       rtx op2 = operands[2];
10781       int i;
10782
10783       if (GET_MODE (op2) != <ssescalarmode>mode)
10784         {
10785           op2 = gen_reg_rtx (<ssescalarmode>mode);
10786           convert_move (op2, operands[2], false);
10787         }
10788
10789       for (i = 0; i < <ssescalarnum>; i++)
10790         RTVEC_ELT (vs, i) = op2;
10791
10792       emit_insn (gen_vec_init<mode> (reg, par));
10793       emit_insn (gen_neg<mode>2 (neg, reg));
10794       emit_insn (gen_sse5_vrotl<mode>3 (operands[0], operands[1], neg));
10795       DONE;
10796     }
10797 })
10798
10799 (define_insn "sse5_rotl<mode>3"
10800   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
10801         (rotate:SSEMODE1248
10802          (match_operand:SSEMODE1248 1 "nonimmediate_operand" "xm")
10803          (match_operand:SI 2 "const_0_to_<sserotatemax>_operand" "n")))]
10804   "TARGET_SSE5"
10805   "prot<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
10806   [(set_attr "type" "sseishft")
10807    (set_attr "mode" "TI")])
10808
10809 (define_insn "sse5_rotr<mode>3"
10810   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
10811         (rotatert:SSEMODE1248
10812          (match_operand:SSEMODE1248 1 "nonimmediate_operand" "xm")
10813          (match_operand:SI 2 "const_0_to_<sserotatemax>_operand" "n")))]
10814   "TARGET_SSE5"
10815 {
10816   operands[3] = GEN_INT ((<ssescalarnum> * 8) - INTVAL (operands[2]));
10817   return \"prot<ssevecsize>\t{%3, %1, %0|%0, %1, %3}\";
10818 }
10819   [(set_attr "type" "sseishft")
10820    (set_attr "mode" "TI")])
10821
10822 (define_expand "vrotr<mode>3"
10823   [(match_operand:SSEMODE1248 0 "register_operand" "")
10824    (match_operand:SSEMODE1248 1 "register_operand" "")
10825    (match_operand:SSEMODE1248 2 "register_operand" "")]
10826   "TARGET_SSE5"
10827 {
10828   rtx reg = gen_reg_rtx (<MODE>mode);
10829   emit_insn (gen_neg<mode>2 (reg, operands[2]));
10830   emit_insn (gen_sse5_vrotl<mode>3 (operands[0], operands[1], reg));
10831   DONE;
10832 })
10833
10834 (define_expand "vrotl<mode>3"
10835   [(match_operand:SSEMODE1248 0 "register_operand" "")
10836    (match_operand:SSEMODE1248 1 "register_operand" "")
10837    (match_operand:SSEMODE1248 2 "register_operand" "")]
10838   "TARGET_SSE5"
10839 {
10840   emit_insn (gen_sse5_vrotl<mode>3 (operands[0], operands[1], operands[2]));
10841   DONE;
10842 })
10843
10844 (define_insn "sse5_vrotl<mode>3"
10845   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x,x")
10846         (if_then_else:SSEMODE1248
10847          (ge:SSEMODE1248
10848           (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm,x")
10849           (const_int 0))
10850          (rotate:SSEMODE1248
10851           (match_operand:SSEMODE1248 1 "nonimmediate_operand" "x,xm")
10852           (match_dup 2))
10853          (rotatert:SSEMODE1248
10854           (match_dup 1)
10855           (neg:SSEMODE1248 (match_dup 2)))))]
10856   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 3, true, 1, false)"
10857   "prot<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
10858   [(set_attr "type" "sseishft")
10859    (set_attr "mode" "TI")])
10860
10861 ;; SSE5 packed shift instructions.
10862 ;; FIXME: add V2DI back in
10863 (define_expand "vlshr<mode>3"
10864   [(match_operand:SSEMODE124 0 "register_operand" "")
10865    (match_operand:SSEMODE124 1 "register_operand" "")
10866    (match_operand:SSEMODE124 2 "register_operand" "")]
10867   "TARGET_SSE5"
10868 {
10869   rtx neg = gen_reg_rtx (<MODE>mode);
10870   emit_insn (gen_neg<mode>2 (neg, operands[2]));
10871   emit_insn (gen_sse5_lshl<mode>3 (operands[0], operands[1], neg));
10872   DONE;
10873 })
10874
10875 (define_expand "vashr<mode>3"
10876   [(match_operand:SSEMODE124 0 "register_operand" "")
10877    (match_operand:SSEMODE124 1 "register_operand" "")
10878    (match_operand:SSEMODE124 2 "register_operand" "")]
10879   "TARGET_SSE5"
10880 {
10881   rtx neg = gen_reg_rtx (<MODE>mode);
10882   emit_insn (gen_neg<mode>2 (neg, operands[2]));
10883   emit_insn (gen_sse5_ashl<mode>3 (operands[0], operands[1], neg));
10884   DONE;
10885 })
10886
10887 (define_expand "vashl<mode>3"
10888   [(match_operand:SSEMODE124 0 "register_operand" "")
10889    (match_operand:SSEMODE124 1 "register_operand" "")
10890    (match_operand:SSEMODE124 2 "register_operand" "")]
10891   "TARGET_SSE5"
10892 {
10893   emit_insn (gen_sse5_ashl<mode>3 (operands[0], operands[1], operands[2]));
10894   DONE;
10895 })
10896
10897 (define_insn "sse5_ashl<mode>3"
10898   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x,x")
10899         (if_then_else:SSEMODE1248
10900          (ge:SSEMODE1248
10901           (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm,x")
10902           (const_int 0))
10903          (ashift:SSEMODE1248
10904           (match_operand:SSEMODE1248 1 "nonimmediate_operand" "x,xm")
10905           (match_dup 2))
10906          (ashiftrt:SSEMODE1248
10907           (match_dup 1)
10908           (neg:SSEMODE1248 (match_dup 2)))))]
10909   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 3, true, 1, false)"
10910   "psha<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
10911   [(set_attr "type" "sseishft")
10912    (set_attr "mode" "TI")])
10913
10914 (define_insn "sse5_lshl<mode>3"
10915   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x,x")
10916         (if_then_else:SSEMODE1248
10917          (ge:SSEMODE1248
10918           (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm,x")
10919           (const_int 0))
10920          (ashift:SSEMODE1248
10921           (match_operand:SSEMODE1248 1 "nonimmediate_operand" "x,xm")
10922           (match_dup 2))
10923          (lshiftrt:SSEMODE1248
10924           (match_dup 1)
10925           (neg:SSEMODE1248 (match_dup 2)))))]
10926   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 3, true, 1, false)"
10927   "pshl<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
10928   [(set_attr "type" "sseishft")
10929    (set_attr "mode" "TI")])
10930
10931 ;; SSE2 doesn't have some shift varients, so define versions for SSE5
10932 (define_expand "ashlv16qi3"
10933   [(match_operand:V16QI 0 "register_operand" "")
10934    (match_operand:V16QI 1 "register_operand" "")
10935    (match_operand:SI 2 "nonmemory_operand" "")]
10936   "TARGET_SSE5"
10937 {
10938   rtvec vs = rtvec_alloc (16);
10939   rtx par = gen_rtx_PARALLEL (V16QImode, vs);
10940   rtx reg = gen_reg_rtx (V16QImode);
10941   int i;
10942   for (i = 0; i < 16; i++)
10943     RTVEC_ELT (vs, i) = operands[2];
10944
10945   emit_insn (gen_vec_initv16qi (reg, par));
10946   emit_insn (gen_sse5_ashlv16qi3 (operands[0], operands[1], reg));
10947   DONE;
10948 })
10949
10950 (define_expand "lshlv16qi3"
10951   [(match_operand:V16QI 0 "register_operand" "")
10952    (match_operand:V16QI 1 "register_operand" "")
10953    (match_operand:SI 2 "nonmemory_operand" "")]
10954   "TARGET_SSE5"
10955 {
10956   rtvec vs = rtvec_alloc (16);
10957   rtx par = gen_rtx_PARALLEL (V16QImode, vs);
10958   rtx reg = gen_reg_rtx (V16QImode);
10959   int i;
10960   for (i = 0; i < 16; i++)
10961     RTVEC_ELT (vs, i) = operands[2];
10962
10963   emit_insn (gen_vec_initv16qi (reg, par));
10964   emit_insn (gen_sse5_lshlv16qi3 (operands[0], operands[1], reg));
10965   DONE;
10966 })
10967
10968 (define_expand "ashrv16qi3"
10969   [(match_operand:V16QI 0 "register_operand" "")
10970    (match_operand:V16QI 1 "register_operand" "")
10971    (match_operand:SI 2 "nonmemory_operand" "")]
10972   "TARGET_SSE5"
10973 {
10974   rtvec vs = rtvec_alloc (16);
10975   rtx par = gen_rtx_PARALLEL (V16QImode, vs);
10976   rtx reg = gen_reg_rtx (V16QImode);
10977   int i;
10978   rtx ele = ((GET_CODE (operands[2]) == CONST_INT)
10979              ? GEN_INT (- INTVAL (operands[2]))
10980              : operands[2]);
10981
10982   for (i = 0; i < 16; i++)
10983     RTVEC_ELT (vs, i) = ele;
10984
10985   emit_insn (gen_vec_initv16qi (reg, par));
10986
10987   if (GET_CODE (operands[2]) != CONST_INT)
10988     {
10989       rtx neg = gen_reg_rtx (V16QImode);
10990       emit_insn (gen_negv16qi2 (neg, reg));
10991       emit_insn (gen_sse5_ashlv16qi3 (operands[0], operands[1], neg));
10992     }
10993   else
10994     emit_insn (gen_sse5_ashlv16qi3 (operands[0], operands[1], reg));
10995
10996   DONE;
10997 })
10998
10999 (define_expand "ashrv2di3"
11000   [(match_operand:V2DI 0 "register_operand" "")
11001    (match_operand:V2DI 1 "register_operand" "")
11002    (match_operand:DI 2 "nonmemory_operand" "")]
11003   "TARGET_SSE5"
11004 {
11005   rtvec vs = rtvec_alloc (2);
11006   rtx par = gen_rtx_PARALLEL (V2DImode, vs);
11007   rtx reg = gen_reg_rtx (V2DImode);
11008   rtx ele;
11009
11010   if (GET_CODE (operands[2]) == CONST_INT)
11011     ele = GEN_INT (- INTVAL (operands[2]));
11012   else if (GET_MODE (operands[2]) != DImode)
11013     {
11014       rtx move = gen_reg_rtx (DImode);
11015       ele = gen_reg_rtx (DImode);
11016       convert_move (move, operands[2], false);
11017       emit_insn (gen_negdi2 (ele, move));
11018     }
11019   else
11020     {
11021       ele = gen_reg_rtx (DImode);
11022       emit_insn (gen_negdi2 (ele, operands[2]));
11023     }
11024
11025   RTVEC_ELT (vs, 0) = ele;
11026   RTVEC_ELT (vs, 1) = ele;
11027   emit_insn (gen_vec_initv2di (reg, par));
11028   emit_insn (gen_sse5_ashlv2di3 (operands[0], operands[1], reg));
11029   DONE;
11030 })
11031
11032 ;; SSE5 FRCZ support
11033 ;; parallel insns
11034 (define_insn "sse5_frcz<mode>2"
11035   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
11036         (unspec:SSEMODEF2P
11037          [(match_operand:SSEMODEF2P 1 "nonimmediate_operand" "xm")]
11038          UNSPEC_FRCZ))]
11039   "TARGET_SSE5"
11040   "frcz<ssemodesuffixf4>\t{%1, %0|%0, %1}"
11041   [(set_attr "type" "ssecvt1")
11042    (set_attr "prefix_extra" "1")
11043    (set_attr "mode" "<MODE>")])
11044
11045 ;; scalar insns
11046 (define_insn "sse5_vmfrcz<mode>2"
11047   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
11048         (vec_merge:SSEMODEF2P
11049           (unspec:SSEMODEF2P
11050            [(match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")]
11051            UNSPEC_FRCZ)
11052           (match_operand:SSEMODEF2P 1 "register_operand" "0")
11053           (const_int 1)))]
11054   "TARGET_SSE5"
11055   "frcz<ssemodesuffixf2s>\t{%2, %0|%0, %2}"
11056   [(set_attr "type" "ssecvt1")
11057    (set_attr "prefix_extra" "1")
11058    (set_attr "mode" "<MODE>")])
11059
11060 (define_insn "sse5_cvtph2ps"
11061   [(set (match_operand:V4SF 0 "register_operand" "=x")
11062         (unspec:V4SF [(match_operand:V4HI 1 "nonimmediate_operand" "xm")]
11063                      UNSPEC_CVTPH2PS))]
11064   "TARGET_SSE5"
11065   "cvtph2ps\t{%1, %0|%0, %1}"
11066   [(set_attr "type" "ssecvt")
11067    (set_attr "mode" "V4SF")])
11068
11069 (define_insn "sse5_cvtps2ph"
11070   [(set (match_operand:V4HI 0 "nonimmediate_operand" "=xm")
11071         (unspec:V4HI [(match_operand:V4SF 1 "register_operand" "x")]
11072                      UNSPEC_CVTPS2PH))]
11073   "TARGET_SSE5"
11074   "cvtps2ph\t{%1, %0|%0, %1}"
11075   [(set_attr "type" "ssecvt")
11076    (set_attr "mode" "V4SF")])
11077
11078 ;; Scalar versions of the com instructions that use vector types that are
11079 ;; called from the intrinsics.  Unlike the the other s{s,d} instructions, the
11080 ;; com instructions fill in 0's in the upper bits instead of leaving them
11081 ;; unmodified, so we use const_vector of 0 instead of match_dup.
11082 (define_expand "sse5_vmmaskcmp<mode>3"
11083   [(set (match_operand:SSEMODEF2P 0 "register_operand" "")
11084         (vec_merge:SSEMODEF2P
11085          (match_operator:SSEMODEF2P 1 "sse5_comparison_float_operator"
11086           [(match_operand:SSEMODEF2P 2 "register_operand" "")
11087            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "")])
11088          (match_dup 4)
11089          (const_int 1)))]
11090   "TARGET_SSE5"
11091 {
11092   operands[4] = CONST0_RTX (<MODE>mode);
11093 })
11094
11095 (define_insn "*sse5_vmmaskcmp<mode>3"
11096   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
11097         (vec_merge:SSEMODEF2P
11098          (match_operator:SSEMODEF2P 1 "sse5_comparison_float_operator"
11099           [(match_operand:SSEMODEF2P 2 "register_operand" "x")
11100            (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm")])
11101           (match_operand:SSEMODEF2P 4 "")
11102           (const_int 1)))]
11103   "TARGET_SSE5"
11104   "com%Y1<ssemodesuffixf2s>\t{%3, %2, %0|%0, %2, %3}"
11105   [(set_attr "type" "sse4arg")
11106    (set_attr "mode" "<ssescalarmode>")])
11107
11108 ;; We don't have a comparison operator that always returns true/false, so
11109 ;; handle comfalse and comtrue specially.
11110 (define_insn "sse5_com_tf<mode>3"
11111   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
11112         (unspec:SSEMODEF2P
11113          [(match_operand:SSEMODEF2P 1 "register_operand" "x")
11114           (match_operand:SSEMODEF2P 2 "nonimmediate_operand" "xm")
11115           (match_operand:SI 3 "const_int_operand" "n")]
11116          UNSPEC_SSE5_TRUEFALSE))]
11117   "TARGET_SSE5"
11118 {
11119   const char *ret = NULL;
11120
11121   switch (INTVAL (operands[3]))
11122     {
11123     case COM_FALSE_S:
11124       ret = \"comfalses<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}\";
11125       break;
11126
11127     case COM_FALSE_P:
11128       ret = \"comfalsep<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}\";
11129       break;
11130
11131     case COM_TRUE_S:
11132       ret = \"comfalses<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}\";
11133       break;
11134
11135     case COM_TRUE_P:
11136       ret = \"comfalsep<ssemodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}\";
11137       break;
11138
11139     default:
11140       gcc_unreachable ();
11141     }
11142
11143   return ret;
11144 }
11145   [(set_attr "type" "ssecmp")
11146    (set_attr "mode" "<MODE>")])
11147
11148 (define_insn "sse5_maskcmp<mode>3"
11149   [(set (match_operand:SSEMODEF2P 0 "register_operand" "=x")
11150         (match_operator:SSEMODEF2P 1 "sse5_comparison_float_operator"
11151          [(match_operand:SSEMODEF2P 2 "register_operand" "x")
11152           (match_operand:SSEMODEF2P 3 "nonimmediate_operand" "xm")]))]
11153   "TARGET_SSE5"
11154   "com%Y1<ssemodesuffixf4>\t{%3, %2, %0|%0, %2, %3}"
11155   [(set_attr "type" "ssecmp")
11156    (set_attr "mode" "<MODE>")])
11157
11158 (define_insn "sse5_maskcmp<mode>3"
11159   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
11160         (match_operator:SSEMODE1248 1 "ix86_comparison_int_operator"
11161          [(match_operand:SSEMODE1248 2 "register_operand" "x")
11162           (match_operand:SSEMODE1248 3 "nonimmediate_operand" "xm")]))]
11163   "TARGET_SSE5"
11164   "pcom%Y1<ssevecsize>\t{%3, %2, %0|%0, %2, %3}"
11165   [(set_attr "type" "sse4arg")
11166    (set_attr "mode" "TI")])
11167
11168 (define_insn "sse5_maskcmp_uns<mode>3"
11169   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
11170         (match_operator:SSEMODE1248 1 "ix86_comparison_uns_operator"
11171          [(match_operand:SSEMODE1248 2 "register_operand" "x")
11172           (match_operand:SSEMODE1248 3 "nonimmediate_operand" "xm")]))]
11173   "TARGET_SSE5"
11174   "pcom%Y1u<ssevecsize>\t{%3, %2, %0|%0, %2, %3}"
11175   [(set_attr "type" "ssecmp")
11176    (set_attr "mode" "TI")])
11177
11178 ;; Version of pcom*u* that is called from the intrinsics that allows pcomequ*
11179 ;; and pcomneu* not to be converted to the signed ones in case somebody needs
11180 ;; the exact instruction generated for the intrinsic.
11181 (define_insn "sse5_maskcmp_uns2<mode>3"
11182   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
11183         (unspec:SSEMODE1248
11184          [(match_operator:SSEMODE1248 1 "ix86_comparison_uns_operator"
11185           [(match_operand:SSEMODE1248 2 "register_operand" "x")
11186            (match_operand:SSEMODE1248 3 "nonimmediate_operand" "xm")])]
11187          UNSPEC_SSE5_UNSIGNED_CMP))]
11188   "TARGET_SSE5"
11189   "pcom%Y1u<ssevecsize>\t{%3, %2, %0|%0, %2, %3}"
11190   [(set_attr "type" "ssecmp")
11191    (set_attr "mode" "TI")])
11192
11193 ;; Pcomtrue and pcomfalse support.  These are useless instructions, but are
11194 ;; being added here to be complete.
11195 (define_insn "sse5_pcom_tf<mode>3"
11196   [(set (match_operand:SSEMODE1248 0 "register_operand" "=x")
11197         (unspec:SSEMODE1248
11198           [(match_operand:SSEMODE1248 1 "register_operand" "x")
11199            (match_operand:SSEMODE1248 2 "nonimmediate_operand" "xm")
11200            (match_operand:SI 3 "const_int_operand" "n")]
11201           UNSPEC_SSE5_TRUEFALSE))]
11202   "TARGET_SSE5"
11203 {
11204   return ((INTVAL (operands[3]) != 0)
11205           ? "pcomtrue<ssevecsize>\t{%2, %1, %0|%0, %1, %2}"
11206           : "pcomfalse<ssevecsize>\t{%2, %1, %0|%0, %1, %2}");
11207 }
11208   [(set_attr "type" "ssecmp")
11209    (set_attr "mode" "TI")])
11210
11211 (define_insn "*avx_aesenc"
11212   [(set (match_operand:V2DI 0 "register_operand" "=x")
11213         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")
11214                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11215                       UNSPEC_AESENC))]
11216   "TARGET_AES && TARGET_AVX"
11217   "vaesenc\t{%2, %1, %0|%0, %1, %2}"
11218   [(set_attr "type" "sselog1")
11219    (set_attr "prefix" "vex")
11220    (set_attr "mode" "TI")])
11221
11222 (define_insn "aesenc"
11223   [(set (match_operand:V2DI 0 "register_operand" "=x")
11224         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
11225                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11226                       UNSPEC_AESENC))]
11227   "TARGET_AES"
11228   "aesenc\t{%2, %0|%0, %2}"
11229   [(set_attr "type" "sselog1")
11230    (set_attr "prefix_extra" "1")
11231    (set_attr "mode" "TI")])
11232
11233 (define_insn "*avx_aesenclast"
11234   [(set (match_operand:V2DI 0 "register_operand" "=x")
11235         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")
11236                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11237                       UNSPEC_AESENCLAST))]
11238   "TARGET_AES && TARGET_AVX"
11239   "vaesenclast\t{%2, %1, %0|%0, %1, %2}"
11240   [(set_attr "type" "sselog1")
11241    (set_attr "prefix" "vex")
11242    (set_attr "mode" "TI")])
11243
11244 (define_insn "aesenclast"
11245   [(set (match_operand:V2DI 0 "register_operand" "=x")
11246         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
11247                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11248                       UNSPEC_AESENCLAST))]
11249   "TARGET_AES"
11250   "aesenclast\t{%2, %0|%0, %2}"
11251   [(set_attr "type" "sselog1")
11252    (set_attr "prefix_extra" "1")
11253    (set_attr "mode" "TI")])
11254
11255 (define_insn "*avx_aesdec"
11256   [(set (match_operand:V2DI 0 "register_operand" "=x")
11257         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")
11258                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11259                       UNSPEC_AESDEC))]
11260   "TARGET_AES && TARGET_AVX"
11261   "vaesdec\t{%2, %1, %0|%0, %1, %2}"
11262   [(set_attr "type" "sselog1")
11263    (set_attr "prefix" "vex")
11264    (set_attr "mode" "TI")])
11265
11266 (define_insn "aesdec"
11267   [(set (match_operand:V2DI 0 "register_operand" "=x")
11268         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
11269                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11270                       UNSPEC_AESDEC))]
11271   "TARGET_AES"
11272   "aesdec\t{%2, %0|%0, %2}"
11273   [(set_attr "type" "sselog1")
11274    (set_attr "prefix_extra" "1")
11275    (set_attr "mode" "TI")])
11276
11277 (define_insn "*avx_aesdeclast"
11278   [(set (match_operand:V2DI 0 "register_operand" "=x")
11279         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")
11280                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11281                       UNSPEC_AESDECLAST))]
11282   "TARGET_AES && TARGET_AVX"
11283   "vaesdeclast\t{%2, %1, %0|%0, %1, %2}"
11284   [(set_attr "type" "sselog1")
11285    (set_attr "prefix" "vex")
11286    (set_attr "mode" "TI")])
11287
11288 (define_insn "aesdeclast"
11289   [(set (match_operand:V2DI 0 "register_operand" "=x")
11290         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
11291                        (match_operand:V2DI 2 "nonimmediate_operand" "xm")]
11292                       UNSPEC_AESDECLAST))]
11293   "TARGET_AES"
11294   "aesdeclast\t{%2, %0|%0, %2}"
11295   [(set_attr "type" "sselog1")
11296    (set_attr "prefix_extra" "1")
11297    (set_attr "mode" "TI")])
11298
11299 (define_insn "aesimc"
11300   [(set (match_operand:V2DI 0 "register_operand" "=x")
11301         (unspec:V2DI [(match_operand:V2DI 1 "nonimmediate_operand" "xm")]
11302                       UNSPEC_AESIMC))]
11303   "TARGET_AES"
11304   "%vaesimc\t{%1, %0|%0, %1}"
11305   [(set_attr "type" "sselog1")
11306    (set_attr "prefix_extra" "1")
11307    (set_attr "prefix" "maybe_vex")
11308    (set_attr "mode" "TI")])
11309
11310 (define_insn "aeskeygenassist"
11311   [(set (match_operand:V2DI 0 "register_operand" "=x")
11312         (unspec:V2DI [(match_operand:V2DI 1 "nonimmediate_operand" "xm")
11313                       (match_operand:SI 2 "const_0_to_255_operand" "n")]
11314                      UNSPEC_AESKEYGENASSIST))]
11315   "TARGET_AES"
11316   "%vaeskeygenassist\t{%2, %1, %0|%0, %1, %2}"
11317   [(set_attr "type" "sselog1")
11318    (set_attr "prefix_extra" "1")
11319    (set_attr "prefix" "maybe_vex")
11320    (set_attr "mode" "TI")])
11321
11322 (define_insn "*vpclmulqdq"
11323   [(set (match_operand:V2DI 0 "register_operand" "=x")
11324         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")
11325                       (match_operand:V2DI 2 "nonimmediate_operand" "xm")
11326                       (match_operand:SI 3 "const_0_to_255_operand" "n")]
11327                      UNSPEC_PCLMUL))]
11328   "TARGET_PCLMUL && TARGET_AVX"
11329   "vpclmulqdq\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11330   [(set_attr "type" "sselog1")
11331    (set_attr "prefix" "vex")
11332    (set_attr "mode" "TI")])
11333
11334 (define_insn "pclmulqdq"
11335   [(set (match_operand:V2DI 0 "register_operand" "=x")
11336         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
11337                       (match_operand:V2DI 2 "nonimmediate_operand" "xm")
11338                       (match_operand:SI 3 "const_0_to_255_operand" "n")]
11339                      UNSPEC_PCLMUL))]
11340   "TARGET_PCLMUL"
11341   "pclmulqdq\t{%3, %2, %0|%0, %2, %3}"
11342   [(set_attr "type" "sselog1")
11343    (set_attr "prefix_extra" "1")
11344    (set_attr "mode" "TI")])
11345
11346 (define_expand "avx_vzeroall"
11347   [(match_par_dup 0 [(const_int 0)])]
11348   "TARGET_AVX"
11349 {
11350   int nregs = TARGET_64BIT ? 16 : 8;
11351   int regno;
11352
11353   operands[0] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (nregs + 1));
11354
11355   XVECEXP (operands[0], 0, 0)
11356     = gen_rtx_UNSPEC_VOLATILE (VOIDmode, gen_rtvec (1, const0_rtx),
11357                                UNSPECV_VZEROALL);
11358
11359   for (regno = 0; regno < nregs; regno++)
11360     XVECEXP (operands[0], 0, regno + 1)
11361       = gen_rtx_SET (VOIDmode,
11362                      gen_rtx_REG (V8SImode, SSE_REGNO (regno)),
11363                      CONST0_RTX (V8SImode));
11364 })
11365
11366 (define_insn "*avx_vzeroall"
11367   [(match_parallel 0 "vzeroall_operation"
11368     [(unspec_volatile [(const_int 0)] UNSPECV_VZEROALL)
11369      (set (match_operand 1 "register_operand" "=x")
11370           (match_operand 2 "const0_operand" "X"))])]
11371   "TARGET_AVX"
11372   "vzeroall"
11373   [(set_attr "type" "sse")
11374    (set_attr "memory" "none")
11375    (set_attr "prefix" "vex")
11376    (set_attr "mode" "OI")])
11377
11378 ;; vzeroupper clobbers the upper 128bits of AVX registers.
11379 (define_insn "avx_vzeroupper"
11380   [(unspec_volatile [(const_int 0)] UNSPECV_VZEROUPPER)
11381    (clobber (reg:V8SI XMM0_REG))
11382    (clobber (reg:V8SI XMM1_REG))
11383    (clobber (reg:V8SI XMM2_REG))
11384    (clobber (reg:V8SI XMM3_REG))
11385    (clobber (reg:V8SI XMM4_REG))
11386    (clobber (reg:V8SI XMM5_REG))
11387    (clobber (reg:V8SI XMM6_REG))
11388    (clobber (reg:V8SI XMM7_REG))]
11389   "TARGET_AVX && !TARGET_64BIT"
11390   "vzeroupper"
11391   [(set_attr "type" "sse")
11392    (set_attr "memory" "none")
11393    (set_attr "prefix" "vex")
11394    (set_attr "mode" "OI")])
11395
11396 (define_insn "avx_vzeroupper_rex64"
11397   [(unspec_volatile [(const_int 0)] UNSPECV_VZEROUPPER)
11398    (clobber (reg:V8SI XMM0_REG))
11399    (clobber (reg:V8SI XMM1_REG))
11400    (clobber (reg:V8SI XMM2_REG))
11401    (clobber (reg:V8SI XMM3_REG))
11402    (clobber (reg:V8SI XMM4_REG))
11403    (clobber (reg:V8SI XMM5_REG))
11404    (clobber (reg:V8SI XMM6_REG))
11405    (clobber (reg:V8SI XMM7_REG))
11406    (clobber (reg:V8SI XMM8_REG))
11407    (clobber (reg:V8SI XMM9_REG))
11408    (clobber (reg:V8SI XMM10_REG))
11409    (clobber (reg:V8SI XMM11_REG))
11410    (clobber (reg:V8SI XMM12_REG))
11411    (clobber (reg:V8SI XMM13_REG))
11412    (clobber (reg:V8SI XMM14_REG))
11413    (clobber (reg:V8SI XMM15_REG))]
11414   "TARGET_AVX && TARGET_64BIT"
11415   "vzeroupper"
11416   [(set_attr "type" "sse")
11417    (set_attr "memory" "none")
11418    (set_attr "prefix" "vex")
11419    (set_attr "mode" "OI")])
11420
11421 (define_insn "avx_vpermil<mode>"
11422   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
11423         (unspec:AVXMODEF2P
11424           [(match_operand:AVXMODEF2P 1 "register_operand" "xm")
11425            (match_operand:SI 2 "const_0_to_<vpermilbits>_operand" "n")]
11426           UNSPEC_VPERMIL))]
11427   "TARGET_AVX"
11428   "vpermilp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
11429   [(set_attr "type" "sselog")
11430    (set_attr "prefix" "vex")
11431    (set_attr "mode" "<MODE>")])
11432
11433 (define_insn "avx_vpermilvar<mode>3"
11434   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
11435         (unspec:AVXMODEF2P
11436           [(match_operand:AVXMODEF2P 1 "register_operand" "x")
11437            (match_operand:<avxpermvecmode> 2 "nonimmediate_operand" "xm")]
11438           UNSPEC_VPERMIL))]
11439   "TARGET_AVX"
11440   "vpermilp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
11441   [(set_attr "type" "sselog")
11442    (set_attr "prefix" "vex")
11443    (set_attr "mode" "<MODE>")])
11444
11445 (define_insn "avx_vperm2f128<mode>3"
11446   [(set (match_operand:AVX256MODE2P 0 "register_operand" "=x")
11447         (unspec:AVX256MODE2P
11448           [(match_operand:AVX256MODE2P 1 "register_operand" "x")
11449            (match_operand:AVX256MODE2P 2 "nonimmediate_operand" "xm")
11450            (match_operand:SI 3 "const_0_to_255_operand" "n")]
11451           UNSPEC_VPERMIL2F128))]
11452   "TARGET_AVX"
11453   "vperm2f128\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11454   [(set_attr "type" "sselog")
11455    (set_attr "prefix" "vex")
11456    (set_attr "mode" "V8SF")])
11457
11458 (define_insn "avx_vbroadcasts<avxmodesuffixf2c><avxmodesuffix>"
11459   [(set (match_operand:AVXMODEF4P 0 "register_operand" "=x")
11460         (vec_concat:AVXMODEF4P
11461           (vec_concat:<avxhalfvecmode>
11462             (match_operand:<avxscalarmode> 1 "memory_operand" "m")
11463             (match_dup 1))
11464           (vec_concat:<avxhalfvecmode>
11465             (match_dup 1)
11466             (match_dup 1))))]
11467   "TARGET_AVX"
11468   "vbroadcasts<avxmodesuffixf2c>\t{%1, %0|%0, %1}"
11469   [(set_attr "type" "ssemov")
11470    (set_attr "prefix" "vex")
11471    (set_attr "mode" "<avxscalarmode>")])
11472
11473 (define_insn "avx_vbroadcastss256"
11474   [(set (match_operand:V8SF 0 "register_operand" "=x")
11475         (vec_concat:V8SF
11476           (vec_concat:V4SF
11477             (vec_concat:V2SF
11478               (match_operand:SF 1 "memory_operand" "m")
11479               (match_dup 1))
11480             (vec_concat:V2SF
11481               (match_dup 1)
11482               (match_dup 1)))
11483           (vec_concat:V4SF
11484             (vec_concat:V2SF
11485               (match_dup 1)
11486               (match_dup 1))
11487             (vec_concat:V2SF
11488               (match_dup 1)
11489               (match_dup 1)))))]
11490   "TARGET_AVX"
11491   "vbroadcastss\t{%1, %0|%0, %1}"
11492   [(set_attr "type" "ssemov")
11493    (set_attr "prefix" "vex")
11494    (set_attr "mode" "SF")])
11495
11496 (define_insn "avx_vbroadcastf128_p<avxmodesuffixf2c>256"
11497   [(set (match_operand:AVX256MODEF2P 0 "register_operand" "=x")
11498         (vec_concat:AVX256MODEF2P
11499           (match_operand:<avxhalfvecmode> 1 "memory_operand" "m")
11500           (match_dup 1)))]
11501   "TARGET_AVX"
11502   "vbroadcastf128\t{%1, %0|%0, %1}"
11503   [(set_attr "type" "ssemov")
11504    (set_attr "prefix" "vex")
11505    (set_attr "mode" "V4SF")])
11506
11507 (define_expand "avx_vinsertf128<mode>"
11508   [(match_operand:AVX256MODE 0 "register_operand" "")
11509    (match_operand:AVX256MODE 1 "register_operand" "")
11510    (match_operand:<avxhalfvecmode> 2 "nonimmediate_operand" "")
11511    (match_operand:SI 3 "const_0_to_1_operand" "")]
11512   "TARGET_AVX"
11513 {
11514   switch (INTVAL (operands[3]))
11515     {
11516     case 0:
11517       emit_insn (gen_vec_set_lo_<mode> (operands[0], operands[1],
11518                                         operands[2]));
11519       break;
11520     case 1:
11521       emit_insn (gen_vec_set_hi_<mode> (operands[0], operands[1],
11522                                         operands[2]));
11523       break;
11524     default:
11525       gcc_unreachable ();
11526     }
11527   DONE;
11528 })
11529
11530 (define_insn "vec_set_lo_<mode>"
11531   [(set (match_operand:AVX256MODE4P 0 "register_operand" "=x")
11532         (vec_concat:AVX256MODE4P
11533           (match_operand:<avxhalfvecmode> 2 "nonimmediate_operand" "xm")
11534           (vec_select:<avxhalfvecmode>
11535             (match_operand:AVX256MODE4P 1 "register_operand" "x")
11536             (parallel [(const_int 2) (const_int 3)]))))]
11537   "TARGET_AVX"
11538   "vinsertf128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
11539   [(set_attr "type" "sselog")
11540    (set_attr "prefix" "vex")
11541    (set_attr "mode" "V8SF")])
11542
11543 (define_insn "vec_set_hi_<mode>"
11544   [(set (match_operand:AVX256MODE4P 0 "register_operand" "=x")
11545         (vec_concat:AVX256MODE4P
11546           (vec_select:<avxhalfvecmode>
11547             (match_operand:AVX256MODE4P 1 "register_operand" "x")
11548             (parallel [(const_int 0) (const_int 1)]))
11549           (match_operand:<avxhalfvecmode> 2 "nonimmediate_operand" "xm")))]
11550   "TARGET_AVX"
11551   "vinsertf128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
11552   [(set_attr "type" "sselog")
11553    (set_attr "prefix" "vex")
11554    (set_attr "mode" "V8SF")])
11555
11556 (define_insn "vec_set_lo_<mode>"
11557   [(set (match_operand:AVX256MODE8P 0 "register_operand" "=x")
11558         (vec_concat:AVX256MODE8P
11559           (match_operand:<avxhalfvecmode> 2 "nonimmediate_operand" "xm")
11560           (vec_select:<avxhalfvecmode>
11561             (match_operand:AVX256MODE8P 1 "register_operand" "x")
11562             (parallel [(const_int 4) (const_int 5)
11563                        (const_int 6) (const_int 7)]))))]
11564   "TARGET_AVX"
11565   "vinsertf128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
11566   [(set_attr "type" "sselog")
11567    (set_attr "prefix" "vex")
11568    (set_attr "mode" "V8SF")])
11569
11570 (define_insn "vec_set_hi_<mode>"
11571   [(set (match_operand:AVX256MODE8P 0 "register_operand" "=x")
11572         (vec_concat:AVX256MODE8P
11573           (vec_select:<avxhalfvecmode>
11574             (match_operand:AVX256MODE8P 1 "register_operand" "x")
11575             (parallel [(const_int 0) (const_int 1)
11576                        (const_int 2) (const_int 3)]))
11577           (match_operand:<avxhalfvecmode> 2 "nonimmediate_operand" "xm")))]
11578   "TARGET_AVX"
11579   "vinsertf128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
11580   [(set_attr "type" "sselog")
11581    (set_attr "prefix" "vex")
11582    (set_attr "mode" "V8SF")])
11583
11584 (define_insn "vec_set_lo_v16hi"
11585   [(set (match_operand:V16HI 0 "register_operand" "=x")
11586         (vec_concat:V16HI
11587           (match_operand:V8HI 2 "nonimmediate_operand" "xm")
11588           (vec_select:V8HI
11589             (match_operand:V16HI 1 "register_operand" "x")
11590             (parallel [(const_int 8) (const_int 9)
11591                        (const_int 10) (const_int 11)
11592                        (const_int 12) (const_int 13)
11593                        (const_int 14) (const_int 15)]))))]
11594   "TARGET_AVX"
11595   "vinsertf128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
11596   [(set_attr "type" "sselog")
11597    (set_attr "prefix" "vex")
11598    (set_attr "mode" "V8SF")])
11599
11600 (define_insn "vec_set_hi_v16hi"
11601   [(set (match_operand:V16HI 0 "register_operand" "=x")
11602         (vec_concat:V16HI
11603           (vec_select:V8HI
11604             (match_operand:V16HI 1 "register_operand" "x")
11605             (parallel [(const_int 0) (const_int 1)
11606                        (const_int 2) (const_int 3)
11607                        (const_int 4) (const_int 5)
11608                        (const_int 6) (const_int 7)]))
11609           (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
11610   "TARGET_AVX"
11611   "vinsertf128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
11612   [(set_attr "type" "sselog")
11613    (set_attr "prefix" "vex")
11614    (set_attr "mode" "V8SF")])
11615
11616 (define_insn "vec_set_lo_v32qi"
11617   [(set (match_operand:V32QI 0 "register_operand" "=x")
11618         (vec_concat:V32QI
11619           (match_operand:V16QI 2 "nonimmediate_operand" "xm")
11620           (vec_select:V16QI
11621             (match_operand:V32QI 1 "register_operand" "x")
11622             (parallel [(const_int 16) (const_int 17)
11623                        (const_int 18) (const_int 19)
11624                        (const_int 20) (const_int 21)
11625                        (const_int 22) (const_int 23)
11626                        (const_int 24) (const_int 25)
11627                        (const_int 26) (const_int 27)
11628                        (const_int 28) (const_int 29)
11629                        (const_int 30) (const_int 31)]))))]
11630   "TARGET_AVX"
11631   "vinsertf128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
11632   [(set_attr "type" "sselog")
11633    (set_attr "prefix" "vex")
11634    (set_attr "mode" "V8SF")])
11635
11636 (define_insn "vec_set_hi_v32qi"
11637   [(set (match_operand:V32QI 0 "register_operand" "=x")
11638         (vec_concat:V32QI
11639           (vec_select:V16QI
11640             (match_operand:V32QI 1 "register_operand" "x")
11641             (parallel [(const_int 0) (const_int 1)
11642                        (const_int 2) (const_int 3)
11643                        (const_int 4) (const_int 5)
11644                        (const_int 6) (const_int 7)
11645                        (const_int 8) (const_int 9)
11646                        (const_int 10) (const_int 11)
11647                        (const_int 12) (const_int 13)
11648                        (const_int 14) (const_int 15)]))
11649           (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
11650   "TARGET_AVX"
11651   "vinsertf128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
11652   [(set_attr "type" "sselog")
11653    (set_attr "prefix" "vex")
11654    (set_attr "mode" "V8SF")])
11655
11656 (define_insn "avx_maskloadp<avxmodesuffixf2c><avxmodesuffix>"
11657   [(set (match_operand:AVXMODEF2P 0 "register_operand" "=x")
11658         (unspec:AVXMODEF2P
11659           [(match_operand:AVXMODEF2P 1 "memory_operand" "m")
11660            (match_operand:<avxpermvecmode> 2 "register_operand" "x")
11661            (match_dup 0)]
11662           UNSPEC_MASKLOAD))]
11663   "TARGET_AVX"
11664   "vmaskmovp<avxmodesuffixf2c>\t{%1, %2, %0|%0, %2, %1}"
11665   [(set_attr "type" "sselog1")
11666    (set_attr "prefix" "vex")
11667    (set_attr "mode" "<MODE>")])
11668
11669 (define_insn "avx_maskstorep<avxmodesuffixf2c><avxmodesuffix>"
11670   [(set (match_operand:AVXMODEF2P 0 "memory_operand" "=m")
11671         (unspec:AVXMODEF2P
11672           [(match_operand:<avxpermvecmode> 1 "register_operand" "x")
11673            (match_operand:AVXMODEF2P 2 "register_operand" "x")
11674            (match_dup 0)]
11675           UNSPEC_MASKSTORE))]
11676   "TARGET_AVX"
11677   "vmaskmovp<avxmodesuffixf2c>\t{%2, %1, %0|%0, %1, %2}"
11678   [(set_attr "type" "sselog1")
11679    (set_attr "prefix" "vex")
11680    (set_attr "mode" "<MODE>")])
11681
11682 (define_insn "avx_<avxmodesuffixp><avxmodesuffix>_<avxmodesuffixp>"
11683   [(set (match_operand:AVX256MODE2P 0 "register_operand" "=x,x")
11684         (unspec:AVX256MODE2P
11685           [(match_operand:<avxhalfvecmode> 1 "nonimmediate_operand" "0,xm")]
11686           UNSPEC_CAST))]
11687   "TARGET_AVX"
11688 {
11689   switch (which_alternative)
11690     {
11691     case 0:
11692       return "";
11693     case 1:
11694       switch (get_attr_mode (insn))
11695         {
11696         case MODE_V8SF:
11697           return "vmovaps\t{%1, %x0|%x0, %1}";
11698         case MODE_V4DF:
11699           return "vmovapd\t{%1, %x0|%x0, %1}";
11700         case MODE_OI:
11701           return "vmovdqa\t{%1, %x0|%x0, %1}";
11702         default:
11703           break;
11704         }
11705     default:
11706       break;
11707     }
11708   gcc_unreachable ();
11709 }
11710   [(set_attr "type" "ssemov")
11711    (set_attr "prefix" "vex")
11712    (set_attr "mode" "<avxvecmode>")
11713    (set (attr "length")
11714     (if_then_else (eq_attr "alternative" "0")
11715        (const_string "0")
11716        (const_string "*")))])
11717
11718 (define_insn "avx_<avxmodesuffixp>_<avxmodesuffixp><avxmodesuffix>"
11719   [(set (match_operand:<avxhalfvecmode> 0 "register_operand" "=x,x")
11720         (unspec:<avxhalfvecmode>
11721           [(match_operand:AVX256MODE2P 1 "nonimmediate_operand" "0,xm")]
11722           UNSPEC_CAST))]
11723   "TARGET_AVX"
11724 {
11725   switch (which_alternative)
11726     {
11727     case 0:
11728       return "";
11729     case 1:
11730       switch (get_attr_mode (insn))
11731         {
11732         case MODE_V8SF:
11733           return "vmovaps\t{%x1, %0|%0, %x1}";
11734         case MODE_V4DF:
11735           return "vmovapd\t{%x1, %0|%0, %x1}";
11736         case MODE_OI:
11737           return "vmovdqa\t{%x1, %0|%0, %x1}";
11738         default:
11739           break;
11740         }
11741     default:
11742       break;
11743     }
11744   gcc_unreachable ();
11745 }
11746   [(set_attr "type" "ssemov")
11747    (set_attr "prefix" "vex")
11748    (set_attr "mode" "<avxvecmode>")
11749    (set (attr "length")
11750     (if_then_else (eq_attr "alternative" "0")
11751        (const_string "0")
11752        (const_string "*")))])
11753
11754 (define_expand "vec_init<mode>"
11755   [(match_operand:AVX256MODE 0 "register_operand" "")
11756    (match_operand 1 "" "")]
11757   "TARGET_AVX"
11758 {
11759   ix86_expand_vector_init (false, operands[0], operands[1]);
11760   DONE;
11761 })
11762
11763 (define_insn "*vec_concat<mode>_avx"
11764   [(set (match_operand:AVX256MODE 0 "register_operand"   "=x,x")
11765         (vec_concat:AVX256MODE
11766           (match_operand:<avxhalfvecmode> 1 "register_operand" "x,x")
11767           (match_operand:<avxhalfvecmode> 2 "vector_move_operand" "xm,C")))]
11768   "TARGET_AVX"
11769 {
11770   switch (which_alternative)
11771     {
11772     case 0:
11773       return "vinsertf128\t{$0x1, %2, %t1, %0|%0, %t1, %2, 0x1}";
11774     case 1:
11775       switch (get_attr_mode (insn))
11776         {
11777         case MODE_V8SF:
11778           return "vmovaps\t{%1, %x0|%x0, %1}";
11779         case MODE_V4DF:
11780           return "vmovapd\t{%1, %x0|%x0, %1}";
11781         default:
11782           return "vmovdqa\t{%1, %x0|%x0, %1}";
11783         }
11784     default:
11785       gcc_unreachable ();
11786     }
11787 }
11788   [(set_attr "type" "sselog,ssemov")
11789    (set_attr "prefix" "vex")
11790    (set_attr "mode" "<avxvecmode>")])