OSDN Git Service

* config/i386/i386.c (ix86_expand_builtin): If gather mask
[pf3gnuchains/gcc-fork.git] / gcc / config / i386 / sse.md
1 ;; GCC machine description for SSE instructions
2 ;; Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011
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 ;; All vector modes including V?TImode, used in move patterns.
22 (define_mode_iterator V16
23   [(V32QI "TARGET_AVX") V16QI
24    (V16HI "TARGET_AVX") V8HI
25    (V8SI "TARGET_AVX") V4SI
26    (V4DI "TARGET_AVX") V2DI
27    (V2TI "TARGET_AVX") V1TI
28    (V8SF "TARGET_AVX") V4SF
29    (V4DF "TARGET_AVX") V2DF])
30
31 ;; All vector modes
32 (define_mode_iterator V
33   [(V32QI "TARGET_AVX") V16QI
34    (V16HI "TARGET_AVX") V8HI
35    (V8SI "TARGET_AVX") V4SI
36    (V4DI "TARGET_AVX") V2DI
37    (V8SF "TARGET_AVX") V4SF
38    (V4DF "TARGET_AVX") (V2DF "TARGET_SSE2")])
39
40 ;; All 128bit vector modes
41 (define_mode_iterator V_128
42   [V16QI V8HI V4SI V2DI V4SF (V2DF "TARGET_SSE2")])
43
44 ;; All 256bit vector modes
45 (define_mode_iterator V_256
46   [V32QI V16HI V8SI V4DI V8SF V4DF])
47
48 ;; All vector float modes
49 (define_mode_iterator VF
50   [(V8SF "TARGET_AVX") V4SF
51    (V4DF "TARGET_AVX") (V2DF "TARGET_SSE2")])
52
53 ;; All SFmode vector float modes
54 (define_mode_iterator VF1
55   [(V8SF "TARGET_AVX") V4SF])
56
57 ;; All DFmode vector float modes
58 (define_mode_iterator VF2
59   [(V4DF "TARGET_AVX") V2DF])
60
61 ;; All 128bit vector float modes
62 (define_mode_iterator VF_128
63   [V4SF (V2DF "TARGET_SSE2")])
64
65 ;; All 256bit vector float modes
66 (define_mode_iterator VF_256
67   [V8SF V4DF])
68
69 ;; All vector integer modes
70 (define_mode_iterator VI
71   [(V32QI "TARGET_AVX") V16QI
72    (V16HI "TARGET_AVX") V8HI
73    (V8SI "TARGET_AVX") V4SI
74    (V4DI "TARGET_AVX") V2DI])
75
76 (define_mode_iterator VI_AVX2
77   [(V32QI "TARGET_AVX2") V16QI
78    (V16HI "TARGET_AVX2") V8HI
79    (V8SI "TARGET_AVX2") V4SI
80    (V4DI "TARGET_AVX2") V2DI])
81
82 ;; All QImode vector integer modes
83 (define_mode_iterator VI1
84   [(V32QI "TARGET_AVX") V16QI])
85
86 ;; All DImode vector integer modes
87 (define_mode_iterator VI8
88   [(V4DI "TARGET_AVX") V2DI])
89
90 (define_mode_iterator VI1_AVX2
91   [(V32QI "TARGET_AVX2") V16QI])
92
93 (define_mode_iterator VI2_AVX2
94   [(V16HI "TARGET_AVX2") V8HI])
95
96 (define_mode_iterator VI4_AVX2
97   [(V8SI "TARGET_AVX2") V4SI])
98
99 (define_mode_iterator VI8_AVX2
100   [(V4DI "TARGET_AVX2") V2DI])
101
102 ;; ??? We should probably use TImode instead.
103 (define_mode_iterator VIMAX_AVX2
104   [(V2TI "TARGET_AVX2") V1TI])
105
106 ;; ??? This should probably be dropped in favor of VIMAX_AVX2.
107 (define_mode_iterator SSESCALARMODE
108   [(V2TI "TARGET_AVX2") TI])
109
110 (define_mode_iterator VI12_AVX2
111   [(V32QI "TARGET_AVX2") V16QI
112    (V16HI "TARGET_AVX2") V8HI])
113
114 (define_mode_iterator VI24_AVX2
115   [(V16HI "TARGET_AVX2") V8HI
116    (V8SI "TARGET_AVX2") V4SI])
117
118 (define_mode_iterator VI124_AVX2
119   [(V32QI "TARGET_AVX2") V16QI
120    (V16HI "TARGET_AVX2") V8HI
121    (V8SI "TARGET_AVX2") V4SI])
122
123 (define_mode_iterator VI248_AVX2
124   [(V16HI "TARGET_AVX2") V8HI
125    (V8SI "TARGET_AVX2") V4SI
126    (V4DI "TARGET_AVX2") V2DI])
127
128 (define_mode_iterator VI48_AVX2
129   [(V8SI "TARGET_AVX2") V4SI
130    (V4DI "TARGET_AVX2") V2DI])
131
132 (define_mode_iterator V48_AVX2
133   [V4SF V2DF
134    V8SF V4DF
135    (V4SI "TARGET_AVX2") (V2DI "TARGET_AVX2")
136    (V8SI "TARGET_AVX2") (V4DI "TARGET_AVX2")])
137
138 (define_mode_attr sse2_avx2
139   [(V16QI "sse2") (V32QI "avx2")
140    (V8HI "sse2") (V16HI "avx2")
141    (V4SI "sse2") (V8SI "avx2")
142    (V2DI "sse2") (V4DI "avx2")
143    (V1TI "sse2") (V2TI "avx2")])
144
145 (define_mode_attr ssse3_avx2
146    [(V16QI "ssse3") (V32QI "avx2")
147     (V8HI "ssse3") (V16HI "avx2")
148     (V4SI "ssse3") (V8SI "avx2")
149     (V2DI "ssse3") (V4DI "avx2")
150     (TI "ssse3") (V2TI "avx2")])
151
152 (define_mode_attr sse4_1_avx2
153    [(V16QI "sse4_1") (V32QI "avx2")
154     (V8HI "sse4_1") (V16HI "avx2")
155     (V4SI "sse4_1") (V8SI "avx2")
156     (V2DI "sse4_1") (V4DI "avx2")])
157
158 (define_mode_attr avx_avx2
159   [(V4SF "avx") (V2DF "avx")
160    (V8SF "avx") (V4DF "avx")
161    (V4SI "avx2") (V2DI "avx2")
162    (V8SI "avx2") (V4DI "avx2")])
163
164 (define_mode_attr vec_avx2
165   [(V16QI "vec") (V32QI "avx2")
166    (V8HI "vec") (V16HI "avx2")
167    (V4SI "vec") (V8SI "avx2")
168    (V2DI "vec") (V4DI "avx2")])
169
170 (define_mode_attr ssedoublemode
171   [(V16HI "V16SI") (V8HI "V8SI")])
172
173 (define_mode_attr ssebytemode
174   [(V4DI "V32QI") (V2DI "V16QI")])
175
176 ;; All 128bit vector integer modes
177 (define_mode_iterator VI_128 [V16QI V8HI V4SI V2DI])
178
179 ;; All 256bit vector integer modes
180 (define_mode_iterator VI_256 [V32QI V16HI V8SI V4DI])
181
182 ;; Random 128bit vector integer mode combinations
183 (define_mode_iterator VI12_128 [V16QI V8HI])
184 (define_mode_iterator VI14_128 [V16QI V4SI])
185 (define_mode_iterator VI124_128 [V16QI V8HI V4SI])
186 (define_mode_iterator VI128_128 [V16QI V8HI V2DI])
187 (define_mode_iterator VI24_128 [V8HI V4SI])
188 (define_mode_iterator VI248_128 [V8HI V4SI V2DI])
189 (define_mode_iterator VI48_128 [V4SI V2DI])
190
191 ;; Random 256bit vector integer mode combinations
192 (define_mode_iterator VI124_256 [V32QI V16HI V8SI])
193 (define_mode_iterator VI48_256 [V8SI V4DI])
194
195 ;; Int-float size matches
196 (define_mode_iterator VI4F_128 [V4SI V4SF])
197 (define_mode_iterator VI8F_128 [V2DI V2DF])
198 (define_mode_iterator VI4F_256 [V8SI V8SF])
199 (define_mode_iterator VI8F_256 [V4DI V4DF])
200
201 ;; Mapping from float mode to required SSE level
202 (define_mode_attr sse
203   [(SF "sse") (DF "sse2")
204    (V4SF "sse") (V2DF "sse2")
205    (V8SF "avx") (V4DF "avx")])
206
207 (define_mode_attr sse2
208   [(V16QI "sse2") (V32QI "avx")
209    (V2DI "sse2") (V4DI "avx")])
210
211 (define_mode_attr sse3
212   [(V16QI "sse3") (V32QI "avx")])
213
214 (define_mode_attr sse4_1
215   [(V4SF "sse4_1") (V2DF "sse4_1")
216    (V8SF "avx") (V4DF "avx")])
217
218 (define_mode_attr avxsizesuffix
219   [(V32QI "256") (V16HI "256") (V8SI "256") (V4DI "256")
220    (V16QI "") (V8HI "") (V4SI "") (V2DI "")
221    (V8SF "256") (V4DF "256")
222    (V4SF "") (V2DF "")])
223
224 ;; SSE instruction mode
225 (define_mode_attr sseinsnmode
226   [(V32QI "OI") (V16HI "OI") (V8SI "OI") (V4DI "OI") (V2TI "OI")
227    (V16QI "TI") (V8HI "TI") (V4SI "TI") (V2DI "TI") (V1TI "TI")
228    (V8SF "V8SF") (V4DF "V4DF")
229    (V4SF "V4SF") (V2DF "V2DF")
230    (TI "TI")])
231
232 ;; Mapping of vector float modes to an integer mode of the same size
233 (define_mode_attr sseintvecmode
234   [(V8SF "V8SI") (V4DF "V4DI")
235    (V4SF "V4SI") (V2DF "V2DI")
236    (V8SI "V8SI") (V4DI "V4DI")
237    (V4SI "V4SI") (V2DI "V2DI")
238    (V16HI "V16HI") (V8HI "V8HI")
239    (V32QI "V32QI") (V16QI "V16QI")])
240
241 (define_mode_attr sseintvecmodelower
242   [(V8SF "v8si") (V4DF "v4di")
243    (V4SF "v4si") (V2DF "v2di")
244    (V8SI "v8si") (V4DI "v4di")
245    (V4SI "v4si") (V2DI "v2di")
246    (V16HI "v16hi") (V8HI "v8hi")
247    (V32QI "v32qi") (V16QI "v16qi")])
248
249 ;; Mapping of vector modes to a vector mode of double size
250 (define_mode_attr ssedoublevecmode
251   [(V32QI "V64QI") (V16HI "V32HI") (V8SI "V16SI") (V4DI "V8DI")
252    (V16QI "V32QI") (V8HI "V16HI") (V4SI "V8SI") (V2DI "V4DI")
253    (V8SF "V16SF") (V4DF "V8DF")
254    (V4SF "V8SF") (V2DF "V4DF")])
255
256 ;; Mapping of vector modes to a vector mode of half size
257 (define_mode_attr ssehalfvecmode
258   [(V32QI "V16QI") (V16HI "V8HI") (V8SI "V4SI") (V4DI "V2DI")
259    (V16QI  "V8QI") (V8HI  "V4HI") (V4SI "V2SI")
260    (V8SF "V4SF") (V4DF "V2DF")
261    (V4SF "V2SF")])
262
263 ;; Mapping of vector modes back to the scalar modes
264 (define_mode_attr ssescalarmode
265   [(V32QI "QI") (V16HI "HI") (V8SI "SI") (V4DI "DI")
266    (V16QI "QI") (V8HI "HI") (V4SI "SI") (V2DI "DI")
267    (V8SF "SF") (V4DF "DF")
268    (V4SF "SF") (V2DF "DF")])
269
270 ;; Number of scalar elements in each vector type
271 (define_mode_attr ssescalarnum
272   [(V32QI "32") (V16HI "16") (V8SI "8") (V4DI "4")
273    (V16QI "16") (V8HI "8") (V4SI "4") (V2DI "2")
274    (V8SF "8") (V4DF "4")
275    (V4SF "4") (V2DF "2")])
276
277 ;; SSE prefix for integer vector modes
278 (define_mode_attr sseintprefix
279   [(V2DI "p") (V2DF "")
280    (V4DI "p") (V4DF "")
281    (V4SI "p") (V4SF "")
282    (V8SI "p") (V8SF "")])
283
284 ;; SSE scalar suffix for vector modes
285 (define_mode_attr ssescalarmodesuffix
286   [(SF "ss") (DF "sd")
287    (V8SF "ss") (V4DF "sd")
288    (V4SF "ss") (V2DF "sd")
289    (V8SI "ss") (V4DI "sd")
290    (V4SI "d")])
291
292 ;; Pack/unpack vector modes
293 (define_mode_attr sseunpackmode
294   [(V16QI "V8HI") (V8HI "V4SI") (V4SI "V2DI")
295    (V32QI "V16HI") (V16HI "V8SI") (V8SI "V4DI")])
296
297 (define_mode_attr ssepackmode
298   [(V8HI "V16QI") (V4SI "V8HI") (V2DI "V4SI")
299    (V16HI "V32QI") (V8SI "V16HI") (V4DI "V8SI")])
300
301 ;; Mapping of the max integer size for xop rotate immediate constraint
302 (define_mode_attr sserotatemax
303   [(V16QI "7") (V8HI "15") (V4SI "31") (V2DI "63")])
304
305 ;; Mapping of mode to cast intrinsic name
306 (define_mode_attr castmode [(V8SI "si") (V8SF "ps") (V4DF "pd")])
307
308 ;; Instruction suffix for sign and zero extensions.
309 (define_code_attr extsuffix [(sign_extend "sx") (zero_extend "zx")])
310
311 ;; i128 for integer vectors and TARGET_AVX2, f128 otherwise.
312 (define_mode_attr i128
313   [(V8SF "f128") (V4DF "f128") (V32QI "%~128") (V16HI "%~128")
314    (V8SI "%~128") (V4DI "%~128")])
315
316 ;; Mix-n-match
317 (define_mode_iterator AVX256MODE2P [V8SI V8SF V4DF])
318
319 (define_mode_iterator FMAMODE [SF DF V4SF V2DF V8SF V4DF])
320
321 ;; Mapping of immediate bits for blend instructions
322 (define_mode_attr blendbits
323   [(V8SF "255") (V4SF "15") (V4DF "15") (V2DF "3")])
324
325 ;; Patterns whose name begins with "sse{,2,3}_" are invoked by intrinsics.
326
327 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
328 ;;
329 ;; Move patterns
330 ;;
331 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
332
333 ;; All of these patterns are enabled for SSE1 as well as SSE2.
334 ;; This is essential for maintaining stable calling conventions.
335
336 (define_expand "mov<mode>"
337   [(set (match_operand:V16 0 "nonimmediate_operand" "")
338         (match_operand:V16 1 "nonimmediate_operand" ""))]
339   "TARGET_SSE"
340 {
341   ix86_expand_vector_move (<MODE>mode, operands);
342   DONE;
343 })
344
345 (define_insn "*mov<mode>_internal"
346   [(set (match_operand:V16 0 "nonimmediate_operand" "=x,x ,m")
347         (match_operand:V16 1 "nonimmediate_or_sse_const_operand"  "C ,xm,x"))]
348   "TARGET_SSE
349    && (register_operand (operands[0], <MODE>mode)
350        || register_operand (operands[1], <MODE>mode))"
351 {
352   switch (which_alternative)
353     {
354     case 0:
355       return standard_sse_constant_opcode (insn, operands[1]);
356     case 1:
357     case 2:
358       switch (get_attr_mode (insn))
359         {
360         case MODE_V8SF:
361         case MODE_V4SF:
362           if (TARGET_AVX
363               && (misaligned_operand (operands[0], <MODE>mode)
364                   || misaligned_operand (operands[1], <MODE>mode)))
365             return "vmovups\t{%1, %0|%0, %1}";
366           else
367             return "%vmovaps\t{%1, %0|%0, %1}";
368
369         case MODE_V4DF:
370         case MODE_V2DF:
371           if (TARGET_AVX
372               && (misaligned_operand (operands[0], <MODE>mode)
373                   || misaligned_operand (operands[1], <MODE>mode)))
374             return "vmovupd\t{%1, %0|%0, %1}";
375           else if (TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
376             return "%vmovaps\t{%1, %0|%0, %1}";
377           else
378             return "%vmovapd\t{%1, %0|%0, %1}";
379
380         case MODE_OI:
381         case MODE_TI:
382           if (TARGET_AVX
383               && (misaligned_operand (operands[0], <MODE>mode)
384                   || misaligned_operand (operands[1], <MODE>mode)))
385             return "vmovdqu\t{%1, %0|%0, %1}";
386           else if (TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
387             return "%vmovaps\t{%1, %0|%0, %1}";
388           else
389             return "%vmovdqa\t{%1, %0|%0, %1}";
390
391         default:
392           gcc_unreachable ();
393         }
394     default:
395       gcc_unreachable ();
396     }
397 }
398   [(set_attr "type" "sselog1,ssemov,ssemov")
399    (set_attr "prefix" "maybe_vex")
400    (set (attr "mode")
401         (cond [(match_test "TARGET_AVX")
402                  (const_string "<sseinsnmode>")
403                (ior (ior (match_test "optimize_function_for_size_p (cfun)")
404                          (not (match_test "TARGET_SSE2")))
405                     (and (eq_attr "alternative" "2")
406                          (match_test "TARGET_SSE_TYPELESS_STORES")))
407                  (const_string "V4SF")
408                (eq (const_string "<MODE>mode") (const_string "V4SFmode"))
409                  (const_string "V4SF")
410                (eq (const_string "<MODE>mode") (const_string "V2DFmode"))
411                  (const_string "V2DF")
412               ]
413           (const_string "TI")))])
414
415 (define_insn "sse2_movq128"
416   [(set (match_operand:V2DI 0 "register_operand" "=x")
417         (vec_concat:V2DI
418           (vec_select:DI
419             (match_operand:V2DI 1 "nonimmediate_operand" "xm")
420             (parallel [(const_int 0)]))
421           (const_int 0)))]
422   "TARGET_SSE2"
423   "%vmovq\t{%1, %0|%0, %1}"
424   [(set_attr "type" "ssemov")
425    (set_attr "prefix" "maybe_vex")
426    (set_attr "mode" "TI")])
427
428 ;; Move a DI from a 32-bit register pair (e.g. %edx:%eax) to an xmm.
429 ;; We'd rather avoid this entirely; if the 32-bit reg pair was loaded
430 ;; from memory, we'd prefer to load the memory directly into the %xmm
431 ;; register.  To facilitate this happy circumstance, this pattern won't
432 ;; split until after register allocation.  If the 64-bit value didn't
433 ;; come from memory, this is the best we can do.  This is much better
434 ;; than storing %edx:%eax into a stack temporary and loading an %xmm
435 ;; from there.
436
437 (define_insn_and_split "movdi_to_sse"
438   [(parallel
439     [(set (match_operand:V4SI 0 "register_operand" "=?x,x")
440           (subreg:V4SI (match_operand:DI 1 "nonimmediate_operand" "r,m") 0))
441      (clobber (match_scratch:V4SI 2 "=&x,X"))])]
442   "!TARGET_64BIT && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES"
443   "#"
444   "&& reload_completed"
445   [(const_int 0)]
446 {
447  if (register_operand (operands[1], DImode))
448    {
449       /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
450          Assemble the 64-bit DImode value in an xmm register.  */
451       emit_insn (gen_sse2_loadld (operands[0], CONST0_RTX (V4SImode),
452                                   gen_rtx_SUBREG (SImode, operands[1], 0)));
453       emit_insn (gen_sse2_loadld (operands[2], CONST0_RTX (V4SImode),
454                                   gen_rtx_SUBREG (SImode, operands[1], 4)));
455       emit_insn (gen_vec_interleave_lowv4si (operands[0], operands[0],
456                                              operands[2]));
457     }
458  else if (memory_operand (operands[1], DImode))
459    emit_insn (gen_vec_concatv2di (gen_lowpart (V2DImode, operands[0]),
460                                   operands[1], const0_rtx));
461  else
462    gcc_unreachable ();
463 })
464
465 (define_split
466   [(set (match_operand:V4SF 0 "register_operand" "")
467         (match_operand:V4SF 1 "zero_extended_scalar_load_operand" ""))]
468   "TARGET_SSE && reload_completed"
469   [(set (match_dup 0)
470         (vec_merge:V4SF
471           (vec_duplicate:V4SF (match_dup 1))
472           (match_dup 2)
473           (const_int 1)))]
474 {
475   operands[1] = simplify_gen_subreg (SFmode, operands[1], V4SFmode, 0);
476   operands[2] = CONST0_RTX (V4SFmode);
477 })
478
479 (define_split
480   [(set (match_operand:V2DF 0 "register_operand" "")
481         (match_operand:V2DF 1 "zero_extended_scalar_load_operand" ""))]
482   "TARGET_SSE2 && reload_completed"
483   [(set (match_dup 0) (vec_concat:V2DF (match_dup 1) (match_dup 2)))]
484 {
485   operands[1] = simplify_gen_subreg (DFmode, operands[1], V2DFmode, 0);
486   operands[2] = CONST0_RTX (DFmode);
487 })
488
489 (define_expand "push<mode>1"
490   [(match_operand:V16 0 "register_operand" "")]
491   "TARGET_SSE"
492 {
493   ix86_expand_push (<MODE>mode, operands[0]);
494   DONE;
495 })
496
497 (define_expand "movmisalign<mode>"
498   [(set (match_operand:V16 0 "nonimmediate_operand" "")
499         (match_operand:V16 1 "nonimmediate_operand" ""))]
500   "TARGET_SSE"
501 {
502   ix86_expand_vector_move_misalign (<MODE>mode, operands);
503   DONE;
504 })
505
506 (define_expand "<sse>_movu<ssemodesuffix><avxsizesuffix>"
507   [(set (match_operand:VF 0 "nonimmediate_operand" "")
508         (unspec:VF
509           [(match_operand:VF 1 "nonimmediate_operand" "")]
510           UNSPEC_MOVU))]
511   "TARGET_SSE"
512 {
513   if (MEM_P (operands[0]) && MEM_P (operands[1]))
514     operands[1] = force_reg (<MODE>mode, operands[1]);
515 })
516
517 (define_insn "*<sse>_movu<ssemodesuffix><avxsizesuffix>"
518   [(set (match_operand:VF 0 "nonimmediate_operand" "=x,m")
519         (unspec:VF
520           [(match_operand:VF 1 "nonimmediate_operand" "xm,x")]
521           UNSPEC_MOVU))]
522   "TARGET_SSE && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
523   "%vmovu<ssemodesuffix>\t{%1, %0|%0, %1}"
524   [(set_attr "type" "ssemov")
525    (set_attr "movu" "1")
526    (set_attr "prefix" "maybe_vex")
527    (set_attr "mode" "<MODE>")])
528
529 (define_expand "<sse2>_movdqu<avxsizesuffix>"
530   [(set (match_operand:VI1 0 "nonimmediate_operand" "")
531         (unspec:VI1 [(match_operand:VI1 1 "nonimmediate_operand" "")]
532                     UNSPEC_MOVU))]
533   "TARGET_SSE2"
534 {
535   if (MEM_P (operands[0]) && MEM_P (operands[1]))
536     operands[1] = force_reg (<MODE>mode, operands[1]);
537 })
538
539 (define_insn "*<sse2>_movdqu<avxsizesuffix>"
540   [(set (match_operand:VI1 0 "nonimmediate_operand" "=x,m")
541         (unspec:VI1 [(match_operand:VI1 1 "nonimmediate_operand" "xm,x")]
542                     UNSPEC_MOVU))]
543   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
544   "%vmovdqu\t{%1, %0|%0, %1}"
545   [(set_attr "type" "ssemov")
546    (set_attr "movu" "1")
547    (set (attr "prefix_data16")
548      (if_then_else
549        (match_test "TARGET_AVX")
550      (const_string "*")
551      (const_string "1")))
552    (set_attr "prefix" "maybe_vex")
553    (set_attr "mode" "<sseinsnmode>")])
554
555 (define_insn "<sse3>_lddqu<avxsizesuffix>"
556   [(set (match_operand:VI1 0 "register_operand" "=x")
557         (unspec:VI1 [(match_operand:VI1 1 "memory_operand" "m")]
558                     UNSPEC_LDDQU))]
559   "TARGET_SSE3"
560   "%vlddqu\t{%1, %0|%0, %1}"
561   [(set_attr "type" "ssemov")
562    (set_attr "movu" "1")
563    (set (attr "prefix_data16")
564      (if_then_else
565        (match_test "TARGET_AVX")
566      (const_string "*")
567      (const_string "0")))
568    (set (attr "prefix_rep")
569      (if_then_else
570        (match_test "TARGET_AVX")
571      (const_string "*")
572      (const_string "1")))
573    (set_attr "prefix" "maybe_vex")
574    (set_attr "mode" "<sseinsnmode>")])
575
576 (define_insn "sse2_movntsi"
577   [(set (match_operand:SI 0 "memory_operand" "=m")
578         (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
579                    UNSPEC_MOVNT))]
580   "TARGET_SSE2"
581   "movnti\t{%1, %0|%0, %1}"
582   [(set_attr "type" "ssemov")
583    (set_attr "prefix_data16" "0")
584    (set_attr "mode" "V2DF")])
585
586 (define_insn "<sse>_movnt<mode>"
587   [(set (match_operand:VF 0 "memory_operand" "=m")
588         (unspec:VF [(match_operand:VF 1 "register_operand" "x")]
589                    UNSPEC_MOVNT))]
590   "TARGET_SSE"
591   "%vmovnt<ssemodesuffix>\t{%1, %0|%0, %1}"
592   [(set_attr "type" "ssemov")
593    (set_attr "prefix" "maybe_vex")
594    (set_attr "mode" "<MODE>")])
595
596 (define_insn "<sse2>_movnt<mode>"
597   [(set (match_operand:VI8 0 "memory_operand" "=m")
598         (unspec:VI8 [(match_operand:VI8 1 "register_operand" "x")]
599                     UNSPEC_MOVNT))]
600   "TARGET_SSE2"
601   "%vmovntdq\t{%1, %0|%0, %1}"
602   [(set_attr "type" "ssecvt")
603    (set (attr "prefix_data16")
604      (if_then_else
605        (match_test "TARGET_AVX")
606      (const_string "*")
607      (const_string "1")))
608    (set_attr "prefix" "maybe_vex")
609    (set_attr "mode" "<sseinsnmode>")])
610
611 ; Expand patterns for non-temporal stores.  At the moment, only those
612 ; that directly map to insns are defined; it would be possible to
613 ; define patterns for other modes that would expand to several insns.
614
615 ;; Modes handled by storent patterns.
616 (define_mode_iterator STORENT_MODE
617   [(SI "TARGET_SSE2") (SF "TARGET_SSE4A") (DF "TARGET_SSE4A")
618    (V2DI "TARGET_SSE2")
619    (V8SF "TARGET_AVX") V4SF
620    (V4DF "TARGET_AVX") (V2DF "TARGET_SSE2")])
621
622 (define_expand "storent<mode>"
623   [(set (match_operand:STORENT_MODE 0 "memory_operand" "")
624         (unspec:STORENT_MODE
625           [(match_operand:STORENT_MODE 1 "register_operand" "")]
626           UNSPEC_MOVNT))]
627   "TARGET_SSE")
628
629 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
630 ;;
631 ;; Parallel floating point arithmetic
632 ;;
633 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
634
635 (define_expand "<code><mode>2"
636   [(set (match_operand:VF 0 "register_operand" "")
637         (absneg:VF
638           (match_operand:VF 1 "register_operand" "")))]
639   "TARGET_SSE"
640   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
641
642 (define_insn_and_split "*absneg<mode>2"
643   [(set (match_operand:VF 0 "register_operand" "=x,x,x,x")
644         (match_operator:VF 3 "absneg_operator"
645           [(match_operand:VF 1 "nonimmediate_operand" "0, xm,x, m")]))
646    (use (match_operand:VF 2 "nonimmediate_operand"    "xm,0, xm,x"))]
647   "TARGET_SSE"
648   "#"
649   "&& reload_completed"
650   [(const_int 0)]
651 {
652   enum rtx_code absneg_op;
653   rtx op1, op2;
654   rtx t;
655
656   if (TARGET_AVX)
657     {
658       if (MEM_P (operands[1]))
659         op1 = operands[2], op2 = operands[1];
660       else
661         op1 = operands[1], op2 = operands[2];
662     }
663   else
664     {
665       op1 = operands[0];
666       if (rtx_equal_p (operands[0], operands[1]))
667         op2 = operands[2];
668       else
669         op2 = operands[1];
670     }
671
672   absneg_op = GET_CODE (operands[3]) == NEG ? XOR : AND;
673   t = gen_rtx_fmt_ee (absneg_op, <MODE>mode, op1, op2);
674   t = gen_rtx_SET (VOIDmode, operands[0], t);
675   emit_insn (t);
676   DONE;
677 }
678   [(set_attr "isa" "noavx,noavx,avx,avx")])
679
680 (define_expand "<plusminus_insn><mode>3"
681   [(set (match_operand:VF 0 "register_operand" "")
682         (plusminus:VF
683           (match_operand:VF 1 "nonimmediate_operand" "")
684           (match_operand:VF 2 "nonimmediate_operand" "")))]
685   "TARGET_SSE"
686   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
687
688 (define_insn "*<plusminus_insn><mode>3"
689   [(set (match_operand:VF 0 "register_operand" "=x,x")
690         (plusminus:VF
691           (match_operand:VF 1 "nonimmediate_operand" "<comm>0,x")
692           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
693   "TARGET_SSE && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
694   "@
695    <plusminus_mnemonic><ssemodesuffix>\t{%2, %0|%0, %2}
696    v<plusminus_mnemonic><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
697   [(set_attr "isa" "noavx,avx")
698    (set_attr "type" "sseadd")
699    (set_attr "prefix" "orig,vex")
700    (set_attr "mode" "<MODE>")])
701
702 (define_insn "<sse>_vm<plusminus_insn><mode>3"
703   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
704         (vec_merge:VF_128
705           (plusminus:VF_128
706             (match_operand:VF_128 1 "register_operand" "0,x")
707             (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm"))
708           (match_dup 1)
709           (const_int 1)))]
710   "TARGET_SSE"
711   "@
712    <plusminus_mnemonic><ssescalarmodesuffix>\t{%2, %0|%0, %2}
713    v<plusminus_mnemonic><ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
714   [(set_attr "isa" "noavx,avx")
715    (set_attr "type" "sseadd")
716    (set_attr "prefix" "orig,vex")
717    (set_attr "mode" "<ssescalarmode>")])
718
719 (define_expand "mul<mode>3"
720   [(set (match_operand:VF 0 "register_operand" "")
721         (mult:VF
722           (match_operand:VF 1 "nonimmediate_operand" "")
723           (match_operand:VF 2 "nonimmediate_operand" "")))]
724   "TARGET_SSE"
725   "ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);")
726
727 (define_insn "*mul<mode>3"
728   [(set (match_operand:VF 0 "register_operand" "=x,x")
729         (mult:VF
730           (match_operand:VF 1 "nonimmediate_operand" "%0,x")
731           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
732   "TARGET_SSE && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
733   "@
734    mul<ssemodesuffix>\t{%2, %0|%0, %2}
735    vmul<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
736   [(set_attr "isa" "noavx,avx")
737    (set_attr "type" "ssemul")
738    (set_attr "prefix" "orig,vex")
739    (set_attr "mode" "<MODE>")])
740
741 (define_insn "<sse>_vmmul<mode>3"
742   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
743         (vec_merge:VF_128
744           (mult:VF_128
745             (match_operand:VF_128 1 "register_operand" "0,x")
746             (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm"))
747           (match_dup 1)
748           (const_int 1)))]
749   "TARGET_SSE"
750   "@
751    mul<ssescalarmodesuffix>\t{%2, %0|%0, %2}
752    vmul<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
753   [(set_attr "isa" "noavx,avx")
754    (set_attr "type" "ssemul")
755    (set_attr "prefix" "orig,vex")
756    (set_attr "mode" "<ssescalarmode>")])
757
758 (define_expand "div<mode>3"
759   [(set (match_operand:VF2 0 "register_operand" "")
760         (div:VF2 (match_operand:VF2 1 "register_operand" "")
761                  (match_operand:VF2 2 "nonimmediate_operand" "")))]
762   "TARGET_SSE2"
763   "ix86_fixup_binary_operands_no_copy (DIV, <MODE>mode, operands);")
764
765 (define_expand "div<mode>3"
766   [(set (match_operand:VF1 0 "register_operand" "")
767         (div:VF1 (match_operand:VF1 1 "register_operand" "")
768                  (match_operand:VF1 2 "nonimmediate_operand" "")))]
769   "TARGET_SSE"
770 {
771   ix86_fixup_binary_operands_no_copy (DIV, <MODE>mode, operands);
772
773   if (TARGET_SSE_MATH
774       && TARGET_RECIP_VEC_DIV
775       && !optimize_insn_for_size_p ()
776       && flag_finite_math_only && !flag_trapping_math
777       && flag_unsafe_math_optimizations)
778     {
779       ix86_emit_swdivsf (operands[0], operands[1], operands[2], <MODE>mode);
780       DONE;
781     }
782 })
783
784 (define_insn "<sse>_div<mode>3"
785   [(set (match_operand:VF 0 "register_operand" "=x,x")
786         (div:VF
787           (match_operand:VF 1 "register_operand" "0,x")
788           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
789   "TARGET_SSE"
790   "@
791    div<ssemodesuffix>\t{%2, %0|%0, %2}
792    vdiv<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
793   [(set_attr "isa" "noavx,avx")
794    (set_attr "type" "ssediv")
795    (set_attr "prefix" "orig,vex")
796    (set_attr "mode" "<MODE>")])
797
798 (define_insn "<sse>_vmdiv<mode>3"
799   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
800         (vec_merge:VF_128
801           (div:VF_128
802             (match_operand:VF_128 1 "register_operand" "0,x")
803             (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm"))
804           (match_dup 1)
805           (const_int 1)))]
806   "TARGET_SSE"
807   "@
808    div<ssescalarmodesuffix>\t{%2, %0|%0, %2}
809    vdiv<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
810   [(set_attr "isa" "noavx,avx")
811    (set_attr "type" "ssediv")
812    (set_attr "prefix" "orig,vex")
813    (set_attr "mode" "<ssescalarmode>")])
814
815 (define_insn "<sse>_rcp<mode>2"
816   [(set (match_operand:VF1 0 "register_operand" "=x")
817         (unspec:VF1
818           [(match_operand:VF1 1 "nonimmediate_operand" "xm")] UNSPEC_RCP))]
819   "TARGET_SSE"
820   "%vrcpps\t{%1, %0|%0, %1}"
821   [(set_attr "type" "sse")
822    (set_attr "atom_sse_attr" "rcp")
823    (set_attr "prefix" "maybe_vex")
824    (set_attr "mode" "<MODE>")])
825
826 (define_insn "sse_vmrcpv4sf2"
827   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
828         (vec_merge:V4SF
829           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm,xm")]
830                        UNSPEC_RCP)
831           (match_operand:V4SF 2 "register_operand" "0,x")
832           (const_int 1)))]
833   "TARGET_SSE"
834   "@
835    rcpss\t{%1, %0|%0, %1}
836    vrcpss\t{%1, %2, %0|%0, %2, %1}"
837   [(set_attr "isa" "noavx,avx")
838    (set_attr "type" "sse")
839    (set_attr "atom_sse_attr" "rcp")
840    (set_attr "prefix" "orig,vex")
841    (set_attr "mode" "SF")])
842
843 (define_expand "sqrt<mode>2"
844   [(set (match_operand:VF2 0 "register_operand" "")
845         (sqrt:VF2 (match_operand:VF2 1 "nonimmediate_operand" "")))]
846   "TARGET_SSE2")
847
848 (define_expand "sqrt<mode>2"
849   [(set (match_operand:VF1 0 "register_operand" "")
850         (sqrt:VF1 (match_operand:VF1 1 "nonimmediate_operand" "")))]
851   "TARGET_SSE"
852 {
853   if (TARGET_SSE_MATH
854       && TARGET_RECIP_VEC_SQRT
855       && !optimize_insn_for_size_p ()
856       && flag_finite_math_only && !flag_trapping_math
857       && flag_unsafe_math_optimizations)
858     {
859       ix86_emit_swsqrtsf (operands[0], operands[1], <MODE>mode, false);
860       DONE;
861     }
862 })
863
864 (define_insn "<sse>_sqrt<mode>2"
865   [(set (match_operand:VF 0 "register_operand" "=x")
866         (sqrt:VF (match_operand:VF 1 "nonimmediate_operand" "xm")))]
867   "TARGET_SSE"
868   "%vsqrt<ssemodesuffix>\t{%1, %0|%0, %1}"
869   [(set_attr "type" "sse")
870    (set_attr "atom_sse_attr" "sqrt")
871    (set_attr "prefix" "maybe_vex")
872    (set_attr "mode" "<MODE>")])
873
874 (define_insn "<sse>_vmsqrt<mode>2"
875   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
876         (vec_merge:VF_128
877           (sqrt:VF_128
878             (match_operand:VF_128 1 "nonimmediate_operand" "xm,xm"))
879           (match_operand:VF_128 2 "register_operand" "0,x")
880           (const_int 1)))]
881   "TARGET_SSE"
882   "@
883    sqrt<ssescalarmodesuffix>\t{%1, %0|%0, %1}
884    vsqrt<ssescalarmodesuffix>\t{%1, %2, %0|%0, %2, %1}"
885   [(set_attr "isa" "noavx,avx")
886    (set_attr "type" "sse")
887    (set_attr "atom_sse_attr" "sqrt")
888    (set_attr "prefix" "orig,vex")
889    (set_attr "mode" "<ssescalarmode>")])
890
891 (define_expand "rsqrt<mode>2"
892   [(set (match_operand:VF1 0 "register_operand" "")
893         (unspec:VF1
894           [(match_operand:VF1 1 "nonimmediate_operand" "")] UNSPEC_RSQRT))]
895   "TARGET_SSE_MATH"
896 {
897   ix86_emit_swsqrtsf (operands[0], operands[1], <MODE>mode, true);
898   DONE;
899 })
900
901 (define_insn "<sse>_rsqrt<mode>2"
902   [(set (match_operand:VF1 0 "register_operand" "=x")
903         (unspec:VF1
904           [(match_operand:VF1 1 "nonimmediate_operand" "xm")] UNSPEC_RSQRT))]
905   "TARGET_SSE"
906   "%vrsqrtps\t{%1, %0|%0, %1}"
907   [(set_attr "type" "sse")
908    (set_attr "prefix" "maybe_vex")
909    (set_attr "mode" "<MODE>")])
910
911 (define_insn "sse_vmrsqrtv4sf2"
912   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
913         (vec_merge:V4SF
914           (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm,xm")]
915                        UNSPEC_RSQRT)
916           (match_operand:V4SF 2 "register_operand" "0,x")
917           (const_int 1)))]
918   "TARGET_SSE"
919   "@
920    rsqrtss\t{%1, %0|%0, %1}
921    vrsqrtss\t{%1, %2, %0|%0, %2, %1}"
922   [(set_attr "isa" "noavx,avx")
923    (set_attr "type" "sse")
924    (set_attr "prefix" "orig,vex")
925    (set_attr "mode" "SF")])
926
927 ;; ??? For !flag_finite_math_only, the representation with SMIN/SMAX
928 ;; isn't really correct, as those rtl operators aren't defined when
929 ;; applied to NaNs.  Hopefully the optimizers won't get too smart on us.
930
931 (define_expand "<code><mode>3"
932   [(set (match_operand:VF 0 "register_operand" "")
933         (smaxmin:VF
934           (match_operand:VF 1 "nonimmediate_operand" "")
935           (match_operand:VF 2 "nonimmediate_operand" "")))]
936   "TARGET_SSE"
937 {
938   if (!flag_finite_math_only)
939     operands[1] = force_reg (<MODE>mode, operands[1]);
940   ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);
941 })
942
943 (define_insn "*<code><mode>3_finite"
944   [(set (match_operand:VF 0 "register_operand" "=x,x")
945         (smaxmin:VF
946           (match_operand:VF 1 "nonimmediate_operand" "%0,x")
947           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
948   "TARGET_SSE && flag_finite_math_only
949    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
950   "@
951    <maxmin_float><ssemodesuffix>\t{%2, %0|%0, %2}
952    v<maxmin_float><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
953   [(set_attr "isa" "noavx,avx")
954    (set_attr "type" "sseadd")
955    (set_attr "prefix" "orig,vex")
956    (set_attr "mode" "<MODE>")])
957
958 (define_insn "*<code><mode>3"
959   [(set (match_operand:VF 0 "register_operand" "=x,x")
960         (smaxmin:VF
961           (match_operand:VF 1 "register_operand" "0,x")
962           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
963   "TARGET_SSE && !flag_finite_math_only"
964   "@
965    <maxmin_float><ssemodesuffix>\t{%2, %0|%0, %2}
966    v<maxmin_float><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
967   [(set_attr "isa" "noavx,avx")
968    (set_attr "type" "sseadd")
969    (set_attr "prefix" "orig,vex")
970    (set_attr "mode" "<MODE>")])
971
972 (define_insn "<sse>_vm<code><mode>3"
973   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
974         (vec_merge:VF_128
975           (smaxmin:VF_128
976             (match_operand:VF_128 1 "register_operand" "0,x")
977             (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm"))
978          (match_dup 1)
979          (const_int 1)))]
980   "TARGET_SSE"
981   "@
982    <maxmin_float><ssescalarmodesuffix>\t{%2, %0|%0, %2}
983    v<maxmin_float><ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
984   [(set_attr "isa" "noavx,avx")
985    (set_attr "type" "sse")
986    (set_attr "prefix" "orig,vex")
987    (set_attr "mode" "<ssescalarmode>")])
988
989 ;; These versions of the min/max patterns implement exactly the operations
990 ;;   min = (op1 < op2 ? op1 : op2)
991 ;;   max = (!(op1 < op2) ? op1 : op2)
992 ;; Their operands are not commutative, and thus they may be used in the
993 ;; presence of -0.0 and NaN.
994
995 (define_insn "*ieee_smin<mode>3"
996   [(set (match_operand:VF 0 "register_operand" "=x,x")
997         (unspec:VF
998           [(match_operand:VF 1 "register_operand" "0,x")
999            (match_operand:VF 2 "nonimmediate_operand" "xm,xm")]
1000          UNSPEC_IEEE_MIN))]
1001   "TARGET_SSE"
1002   "@
1003    min<ssemodesuffix>\t{%2, %0|%0, %2}
1004    vmin<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1005   [(set_attr "isa" "noavx,avx")
1006    (set_attr "type" "sseadd")
1007    (set_attr "prefix" "orig,vex")
1008    (set_attr "mode" "<MODE>")])
1009
1010 (define_insn "*ieee_smax<mode>3"
1011   [(set (match_operand:VF 0 "register_operand" "=x,x")
1012         (unspec:VF
1013           [(match_operand:VF 1 "register_operand" "0,x")
1014            (match_operand:VF 2 "nonimmediate_operand" "xm,xm")]
1015          UNSPEC_IEEE_MAX))]
1016   "TARGET_SSE"
1017   "@
1018    max<ssemodesuffix>\t{%2, %0|%0, %2}
1019    vmax<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1020   [(set_attr "isa" "noavx,avx")
1021    (set_attr "type" "sseadd")
1022    (set_attr "prefix" "orig,vex")
1023    (set_attr "mode" "<MODE>")])
1024
1025 (define_insn "avx_addsubv4df3"
1026   [(set (match_operand:V4DF 0 "register_operand" "=x")
1027         (vec_merge:V4DF
1028           (plus:V4DF
1029             (match_operand:V4DF 1 "register_operand" "x")
1030             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
1031           (minus:V4DF (match_dup 1) (match_dup 2))
1032           (const_int 10)))]
1033   "TARGET_AVX"
1034   "vaddsubpd\t{%2, %1, %0|%0, %1, %2}"
1035   [(set_attr "type" "sseadd")
1036    (set_attr "prefix" "vex")
1037    (set_attr "mode" "V4DF")])
1038
1039 (define_insn "sse3_addsubv2df3"
1040   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
1041         (vec_merge:V2DF
1042           (plus:V2DF
1043             (match_operand:V2DF 1 "register_operand" "0,x")
1044             (match_operand:V2DF 2 "nonimmediate_operand" "xm,xm"))
1045           (minus:V2DF (match_dup 1) (match_dup 2))
1046           (const_int 2)))]
1047   "TARGET_SSE3"
1048   "@
1049    addsubpd\t{%2, %0|%0, %2}
1050    vaddsubpd\t{%2, %1, %0|%0, %1, %2}"
1051   [(set_attr "isa" "noavx,avx")
1052    (set_attr "type" "sseadd")
1053    (set_attr "atom_unit" "complex")
1054    (set_attr "prefix" "orig,vex")
1055    (set_attr "mode" "V2DF")])
1056
1057 (define_insn "avx_addsubv8sf3"
1058   [(set (match_operand:V8SF 0 "register_operand" "=x")
1059         (vec_merge:V8SF
1060           (plus:V8SF
1061             (match_operand:V8SF 1 "register_operand" "x")
1062             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
1063           (minus:V8SF (match_dup 1) (match_dup 2))
1064           (const_int 170)))]
1065   "TARGET_AVX"
1066   "vaddsubps\t{%2, %1, %0|%0, %1, %2}"
1067   [(set_attr "type" "sseadd")
1068    (set_attr "prefix" "vex")
1069    (set_attr "mode" "V8SF")])
1070
1071 (define_insn "sse3_addsubv4sf3"
1072   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
1073         (vec_merge:V4SF
1074           (plus:V4SF
1075             (match_operand:V4SF 1 "register_operand" "0,x")
1076             (match_operand:V4SF 2 "nonimmediate_operand" "xm,xm"))
1077           (minus:V4SF (match_dup 1) (match_dup 2))
1078           (const_int 10)))]
1079   "TARGET_SSE3"
1080   "@
1081    addsubps\t{%2, %0|%0, %2}
1082    vaddsubps\t{%2, %1, %0|%0, %1, %2}"
1083   [(set_attr "isa" "noavx,avx")
1084    (set_attr "type" "sseadd")
1085    (set_attr "prefix" "orig,vex")
1086    (set_attr "prefix_rep" "1,*")
1087    (set_attr "mode" "V4SF")])
1088
1089 (define_insn "avx_h<plusminus_insn>v4df3"
1090   [(set (match_operand:V4DF 0 "register_operand" "=x")
1091         (vec_concat:V4DF
1092           (vec_concat:V2DF
1093             (plusminus:DF
1094               (vec_select:DF
1095                 (match_operand:V4DF 1 "register_operand" "x")
1096                 (parallel [(const_int 0)]))
1097               (vec_select:DF (match_dup 1) (parallel [(const_int 1)])))
1098             (plusminus:DF
1099               (vec_select:DF (match_dup 1) (parallel [(const_int 2)]))
1100               (vec_select:DF (match_dup 1) (parallel [(const_int 3)]))))
1101           (vec_concat:V2DF
1102             (plusminus:DF
1103               (vec_select:DF
1104                 (match_operand:V4DF 2 "nonimmediate_operand" "xm")
1105                 (parallel [(const_int 0)]))
1106               (vec_select:DF (match_dup 2) (parallel [(const_int 1)])))
1107             (plusminus:DF
1108               (vec_select:DF (match_dup 2) (parallel [(const_int 2)]))
1109               (vec_select:DF (match_dup 2) (parallel [(const_int 3)]))))))]
1110   "TARGET_AVX"
1111   "vh<plusminus_mnemonic>pd\t{%2, %1, %0|%0, %1, %2}"
1112   [(set_attr "type" "sseadd")
1113    (set_attr "prefix" "vex")
1114    (set_attr "mode" "V4DF")])
1115
1116 (define_insn "sse3_h<plusminus_insn>v2df3"
1117   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
1118         (vec_concat:V2DF
1119           (plusminus:DF
1120             (vec_select:DF
1121               (match_operand:V2DF 1 "register_operand" "0,x")
1122               (parallel [(const_int 0)]))
1123             (vec_select:DF (match_dup 1) (parallel [(const_int 1)])))
1124           (plusminus:DF
1125             (vec_select:DF
1126               (match_operand:V2DF 2 "nonimmediate_operand" "xm,xm")
1127               (parallel [(const_int 0)]))
1128             (vec_select:DF (match_dup 2) (parallel [(const_int 1)])))))]
1129   "TARGET_SSE3"
1130   "@
1131    h<plusminus_mnemonic>pd\t{%2, %0|%0, %2}
1132    vh<plusminus_mnemonic>pd\t{%2, %1, %0|%0, %1, %2}"
1133   [(set_attr "isa" "noavx,avx")
1134    (set_attr "type" "sseadd")
1135    (set_attr "prefix" "orig,vex")
1136    (set_attr "mode" "V2DF")])
1137
1138 (define_insn "avx_h<plusminus_insn>v8sf3"
1139   [(set (match_operand:V8SF 0 "register_operand" "=x")
1140         (vec_concat:V8SF
1141           (vec_concat:V4SF
1142             (vec_concat:V2SF
1143               (plusminus:SF
1144                 (vec_select:SF
1145                   (match_operand:V8SF 1 "register_operand" "x")
1146                   (parallel [(const_int 0)]))
1147                 (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
1148               (plusminus:SF
1149                 (vec_select:SF (match_dup 1) (parallel [(const_int 2)]))
1150                 (vec_select:SF (match_dup 1) (parallel [(const_int 3)]))))
1151             (vec_concat:V2SF
1152               (plusminus:SF
1153                 (vec_select:SF
1154                   (match_operand:V8SF 2 "nonimmediate_operand" "xm")
1155                   (parallel [(const_int 0)]))
1156                 (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))
1157               (plusminus:SF
1158                 (vec_select:SF (match_dup 2) (parallel [(const_int 2)]))
1159                 (vec_select:SF (match_dup 2) (parallel [(const_int 3)])))))
1160           (vec_concat:V4SF
1161             (vec_concat:V2SF
1162               (plusminus:SF
1163                 (vec_select:SF (match_dup 1) (parallel [(const_int 4)]))
1164                 (vec_select:SF (match_dup 1) (parallel [(const_int 5)])))
1165               (plusminus:SF
1166                 (vec_select:SF (match_dup 1) (parallel [(const_int 6)]))
1167                 (vec_select:SF (match_dup 1) (parallel [(const_int 7)]))))
1168             (vec_concat:V2SF
1169               (plusminus:SF
1170                 (vec_select:SF (match_dup 2) (parallel [(const_int 4)]))
1171                 (vec_select:SF (match_dup 2) (parallel [(const_int 5)])))
1172               (plusminus:SF
1173                 (vec_select:SF (match_dup 2) (parallel [(const_int 6)]))
1174                 (vec_select:SF (match_dup 2) (parallel [(const_int 7)])))))))]
1175   "TARGET_AVX"
1176   "vh<plusminus_mnemonic>ps\t{%2, %1, %0|%0, %1, %2}"
1177   [(set_attr "type" "sseadd")
1178    (set_attr "prefix" "vex")
1179    (set_attr "mode" "V8SF")])
1180
1181 (define_insn "sse3_h<plusminus_insn>v4sf3"
1182   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
1183         (vec_concat:V4SF
1184           (vec_concat:V2SF
1185             (plusminus:SF
1186               (vec_select:SF
1187                 (match_operand:V4SF 1 "register_operand" "0,x")
1188                 (parallel [(const_int 0)]))
1189               (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
1190             (plusminus:SF
1191               (vec_select:SF (match_dup 1) (parallel [(const_int 2)]))
1192               (vec_select:SF (match_dup 1) (parallel [(const_int 3)]))))
1193           (vec_concat:V2SF
1194             (plusminus:SF
1195               (vec_select:SF
1196                 (match_operand:V4SF 2 "nonimmediate_operand" "xm,xm")
1197                 (parallel [(const_int 0)]))
1198               (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))
1199             (plusminus:SF
1200               (vec_select:SF (match_dup 2) (parallel [(const_int 2)]))
1201               (vec_select:SF (match_dup 2) (parallel [(const_int 3)]))))))]
1202   "TARGET_SSE3"
1203   "@
1204    h<plusminus_mnemonic>ps\t{%2, %0|%0, %2}
1205    vh<plusminus_mnemonic>ps\t{%2, %1, %0|%0, %1, %2}"
1206   [(set_attr "isa" "noavx,avx")
1207    (set_attr "type" "sseadd")
1208    (set_attr "atom_unit" "complex")
1209    (set_attr "prefix" "orig,vex")
1210    (set_attr "prefix_rep" "1,*")
1211    (set_attr "mode" "V4SF")])
1212
1213 (define_expand "reduc_splus_v4df"
1214   [(match_operand:V4DF 0 "register_operand" "")
1215    (match_operand:V4DF 1 "register_operand" "")]
1216   "TARGET_AVX"
1217 {
1218   rtx tmp = gen_reg_rtx (V4DFmode);
1219   rtx tmp2 = gen_reg_rtx (V4DFmode);
1220   emit_insn (gen_avx_haddv4df3 (tmp, operands[1], operands[1]));
1221   emit_insn (gen_avx_vperm2f128v4df3 (tmp2, tmp, tmp, GEN_INT (1)));
1222   emit_insn (gen_addv4df3 (operands[0], tmp, tmp2));
1223   DONE;
1224 })
1225
1226 (define_expand "reduc_splus_v2df"
1227   [(match_operand:V2DF 0 "register_operand" "")
1228    (match_operand:V2DF 1 "register_operand" "")]
1229   "TARGET_SSE3"
1230 {
1231   emit_insn (gen_sse3_haddv2df3 (operands[0], operands[1], operands[1]));
1232   DONE;
1233 })
1234
1235 (define_expand "reduc_splus_v8sf"
1236   [(match_operand:V8SF 0 "register_operand" "")
1237    (match_operand:V8SF 1 "register_operand" "")]
1238   "TARGET_AVX"
1239 {
1240   rtx tmp = gen_reg_rtx (V8SFmode);
1241   rtx tmp2 = gen_reg_rtx (V8SFmode);
1242   emit_insn (gen_avx_haddv8sf3 (tmp, operands[1], operands[1]));
1243   emit_insn (gen_avx_haddv8sf3 (tmp2, tmp, tmp));
1244   emit_insn (gen_avx_vperm2f128v8sf3 (tmp, tmp2, tmp2, GEN_INT (1)));
1245   emit_insn (gen_addv8sf3 (operands[0], tmp, tmp2));
1246   DONE;
1247 })
1248
1249 (define_expand "reduc_splus_v4sf"
1250   [(match_operand:V4SF 0 "register_operand" "")
1251    (match_operand:V4SF 1 "register_operand" "")]
1252   "TARGET_SSE"
1253 {
1254   if (TARGET_SSE3)
1255     {
1256       rtx tmp = gen_reg_rtx (V4SFmode);
1257       emit_insn (gen_sse3_haddv4sf3 (tmp, operands[1], operands[1]));
1258       emit_insn (gen_sse3_haddv4sf3 (operands[0], tmp, tmp));
1259     }
1260   else
1261     ix86_expand_reduc (gen_addv4sf3, operands[0], operands[1]);
1262   DONE;
1263 })
1264
1265 ;; Modes handled by reduc_sm{in,ax}* patterns.
1266 (define_mode_iterator REDUC_SMINMAX_MODE
1267   [(V32QI "TARGET_AVX2") (V16HI "TARGET_AVX2")
1268    (V8SI "TARGET_AVX2") (V4DI "TARGET_AVX2")
1269    (V8SF "TARGET_AVX") (V4DF "TARGET_AVX")
1270    (V4SF "TARGET_SSE")])
1271
1272 (define_expand "reduc_<code>_<mode>"
1273   [(smaxmin:REDUC_SMINMAX_MODE
1274      (match_operand:REDUC_SMINMAX_MODE 0 "register_operand" "")
1275      (match_operand:REDUC_SMINMAX_MODE 1 "register_operand" ""))]
1276   ""
1277 {
1278   ix86_expand_reduc (gen_<code><mode>3, operands[0], operands[1]);
1279   DONE;
1280 })
1281
1282 (define_expand "reduc_<code>_<mode>"
1283   [(umaxmin:VI_256
1284      (match_operand:VI_256 0 "register_operand" "")
1285      (match_operand:VI_256 1 "register_operand" ""))]
1286   "TARGET_AVX2"
1287 {
1288   ix86_expand_reduc (gen_<code><mode>3, operands[0], operands[1]);
1289   DONE;
1290 })
1291
1292 (define_expand "reduc_umin_v8hi"
1293   [(umin:V8HI
1294      (match_operand:V8HI 0 "register_operand" "")
1295      (match_operand:V8HI 1 "register_operand" ""))]
1296   "TARGET_SSE4_1"
1297 {
1298   ix86_expand_reduc (gen_uminv8hi3, operands[0], operands[1]);
1299   DONE;
1300 })
1301
1302 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1303 ;;
1304 ;; Parallel floating point comparisons
1305 ;;
1306 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1307
1308 (define_insn "avx_cmp<mode>3"
1309   [(set (match_operand:VF 0 "register_operand" "=x")
1310         (unspec:VF
1311           [(match_operand:VF 1 "register_operand" "x")
1312            (match_operand:VF 2 "nonimmediate_operand" "xm")
1313            (match_operand:SI 3 "const_0_to_31_operand" "n")]
1314           UNSPEC_PCMP))]
1315   "TARGET_AVX"
1316   "vcmp<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1317   [(set_attr "type" "ssecmp")
1318    (set_attr "length_immediate" "1")
1319    (set_attr "prefix" "vex")
1320    (set_attr "mode" "<MODE>")])
1321
1322 (define_insn "avx_vmcmp<mode>3"
1323   [(set (match_operand:VF_128 0 "register_operand" "=x")
1324         (vec_merge:VF_128
1325           (unspec:VF_128
1326             [(match_operand:VF_128 1 "register_operand" "x")
1327              (match_operand:VF_128 2 "nonimmediate_operand" "xm")
1328              (match_operand:SI 3 "const_0_to_31_operand" "n")]
1329             UNSPEC_PCMP)
1330          (match_dup 1)
1331          (const_int 1)))]
1332   "TARGET_AVX"
1333   "vcmp<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1334   [(set_attr "type" "ssecmp")
1335    (set_attr "length_immediate" "1")
1336    (set_attr "prefix" "vex")
1337    (set_attr "mode" "<ssescalarmode>")])
1338
1339 (define_insn "*<sse>_maskcmp<mode>3_comm"
1340   [(set (match_operand:VF 0 "register_operand" "=x,x")
1341         (match_operator:VF 3 "sse_comparison_operator"
1342           [(match_operand:VF 1 "register_operand" "%0,x")
1343            (match_operand:VF 2 "nonimmediate_operand" "xm,xm")]))]
1344   "TARGET_SSE
1345    && GET_RTX_CLASS (GET_CODE (operands[3])) == RTX_COMM_COMPARE"
1346   "@
1347    cmp%D3<ssemodesuffix>\t{%2, %0|%0, %2}
1348    vcmp%D3<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1349   [(set_attr "isa" "noavx,avx")
1350    (set_attr "type" "ssecmp")
1351    (set_attr "length_immediate" "1")
1352    (set_attr "prefix" "orig,vex")
1353    (set_attr "mode" "<MODE>")])
1354
1355 (define_insn "<sse>_maskcmp<mode>3"
1356   [(set (match_operand:VF 0 "register_operand" "=x,x")
1357         (match_operator:VF 3 "sse_comparison_operator"
1358           [(match_operand:VF 1 "register_operand" "0,x")
1359            (match_operand:VF 2 "nonimmediate_operand" "xm,xm")]))]
1360   "TARGET_SSE"
1361   "@
1362    cmp%D3<ssemodesuffix>\t{%2, %0|%0, %2}
1363    vcmp%D3<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1364   [(set_attr "isa" "noavx,avx")
1365    (set_attr "type" "ssecmp")
1366    (set_attr "length_immediate" "1")
1367    (set_attr "prefix" "orig,vex")
1368    (set_attr "mode" "<MODE>")])
1369
1370 (define_insn "<sse>_vmmaskcmp<mode>3"
1371   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
1372         (vec_merge:VF_128
1373          (match_operator:VF_128 3 "sse_comparison_operator"
1374            [(match_operand:VF_128 1 "register_operand" "0,x")
1375             (match_operand:VF_128 2 "nonimmediate_operand" "xm,xm")])
1376          (match_dup 1)
1377          (const_int 1)))]
1378   "TARGET_SSE"
1379   "@
1380    cmp%D3<ssescalarmodesuffix>\t{%2, %0|%0, %2}
1381    vcmp%D3<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1382   [(set_attr "isa" "noavx,avx")
1383    (set_attr "type" "ssecmp")
1384    (set_attr "length_immediate" "1,*")
1385    (set_attr "prefix" "orig,vex")
1386    (set_attr "mode" "<ssescalarmode>")])
1387
1388 (define_insn "<sse>_comi"
1389   [(set (reg:CCFP FLAGS_REG)
1390         (compare:CCFP
1391           (vec_select:MODEF
1392             (match_operand:<ssevecmode> 0 "register_operand" "x")
1393             (parallel [(const_int 0)]))
1394           (vec_select:MODEF
1395             (match_operand:<ssevecmode> 1 "nonimmediate_operand" "xm")
1396             (parallel [(const_int 0)]))))]
1397   "SSE_FLOAT_MODE_P (<MODE>mode)"
1398   "%vcomi<ssemodesuffix>\t{%1, %0|%0, %1}"
1399   [(set_attr "type" "ssecomi")
1400    (set_attr "prefix" "maybe_vex")
1401    (set_attr "prefix_rep" "0")
1402    (set (attr "prefix_data16")
1403         (if_then_else (eq_attr "mode" "DF")
1404                       (const_string "1")
1405                       (const_string "0")))
1406    (set_attr "mode" "<MODE>")])
1407
1408 (define_insn "<sse>_ucomi"
1409   [(set (reg:CCFPU FLAGS_REG)
1410         (compare:CCFPU
1411           (vec_select:MODEF
1412             (match_operand:<ssevecmode> 0 "register_operand" "x")
1413             (parallel [(const_int 0)]))
1414           (vec_select:MODEF
1415             (match_operand:<ssevecmode> 1 "nonimmediate_operand" "xm")
1416             (parallel [(const_int 0)]))))]
1417   "SSE_FLOAT_MODE_P (<MODE>mode)"
1418   "%vucomi<ssemodesuffix>\t{%1, %0|%0, %1}"
1419   [(set_attr "type" "ssecomi")
1420    (set_attr "prefix" "maybe_vex")
1421    (set_attr "prefix_rep" "0")
1422    (set (attr "prefix_data16")
1423         (if_then_else (eq_attr "mode" "DF")
1424                       (const_string "1")
1425                       (const_string "0")))
1426    (set_attr "mode" "<MODE>")])
1427
1428 (define_expand "vcond<V_256:mode><VF_256:mode>"
1429   [(set (match_operand:V_256 0 "register_operand" "")
1430         (if_then_else:V_256
1431           (match_operator 3 ""
1432             [(match_operand:VF_256 4 "nonimmediate_operand" "")
1433              (match_operand:VF_256 5 "nonimmediate_operand" "")])
1434           (match_operand:V_256 1 "general_operand" "")
1435           (match_operand:V_256 2 "general_operand" "")))]
1436   "TARGET_AVX
1437    && (GET_MODE_NUNITS (<V_256:MODE>mode)
1438        == GET_MODE_NUNITS (<VF_256:MODE>mode))"
1439 {
1440   bool ok = ix86_expand_fp_vcond (operands);
1441   gcc_assert (ok);
1442   DONE;
1443 })
1444
1445 (define_expand "vcond<V_128:mode><VF_128:mode>"
1446   [(set (match_operand:V_128 0 "register_operand" "")
1447         (if_then_else:V_128
1448           (match_operator 3 ""
1449             [(match_operand:VF_128 4 "nonimmediate_operand" "")
1450              (match_operand:VF_128 5 "nonimmediate_operand" "")])
1451           (match_operand:V_128 1 "general_operand" "")
1452           (match_operand:V_128 2 "general_operand" "")))]
1453   "TARGET_SSE
1454    && (GET_MODE_NUNITS (<V_128:MODE>mode)
1455        == GET_MODE_NUNITS (<VF_128:MODE>mode))"
1456 {
1457   bool ok = ix86_expand_fp_vcond (operands);
1458   gcc_assert (ok);
1459   DONE;
1460 })
1461
1462 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1463 ;;
1464 ;; Parallel floating point logical operations
1465 ;;
1466 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1467
1468 (define_insn "<sse>_andnot<mode>3"
1469   [(set (match_operand:VF 0 "register_operand" "=x,x")
1470         (and:VF
1471           (not:VF
1472             (match_operand:VF 1 "register_operand" "0,x"))
1473           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
1474   "TARGET_SSE"
1475 {
1476   static char buf[32];
1477   const char *insn;
1478   const char *suffix
1479     = TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL ? "ps" : "<ssemodesuffix>";
1480
1481   switch (which_alternative)
1482     {
1483     case 0:
1484       insn = "andn%s\t{%%2, %%0|%%0, %%2}";
1485       break;
1486     case 1:
1487       insn = "vandn%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
1488       break;
1489     default:
1490       gcc_unreachable ();
1491     }
1492
1493   snprintf (buf, sizeof (buf), insn, suffix);
1494   return buf;
1495 }
1496   [(set_attr "isa" "noavx,avx")
1497    (set_attr "type" "sselog")
1498    (set_attr "prefix" "orig,vex")
1499    (set_attr "mode" "<MODE>")])
1500
1501 (define_expand "<code><mode>3"
1502   [(set (match_operand:VF 0 "register_operand" "")
1503         (any_logic:VF
1504           (match_operand:VF 1 "nonimmediate_operand" "")
1505           (match_operand:VF 2 "nonimmediate_operand" "")))]
1506   "TARGET_SSE"
1507   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
1508
1509 (define_insn "*<code><mode>3"
1510   [(set (match_operand:VF 0 "register_operand" "=x,x")
1511         (any_logic:VF
1512           (match_operand:VF 1 "nonimmediate_operand" "%0,x")
1513           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")))]
1514   "TARGET_SSE && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
1515 {
1516   static char buf[32];
1517   const char *insn;
1518   const char *suffix
1519     = TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL ? "ps" : "<ssemodesuffix>";
1520
1521   switch (which_alternative)
1522     {
1523     case 0:
1524       insn = "<logic>%s\t{%%2, %%0|%%0, %%2}";
1525       break;
1526     case 1:
1527       insn = "v<logic>%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
1528       break;
1529     default:
1530       gcc_unreachable ();
1531     }
1532
1533   snprintf (buf, sizeof (buf), insn, suffix);
1534   return buf;
1535 }
1536   [(set_attr "isa" "noavx,avx")
1537    (set_attr "type" "sselog")
1538    (set_attr "prefix" "orig,vex")
1539    (set_attr "mode" "<MODE>")])
1540
1541 (define_expand "copysign<mode>3"
1542   [(set (match_dup 4)
1543         (and:VF
1544           (not:VF (match_dup 3))
1545           (match_operand:VF 1 "nonimmediate_operand" "")))
1546    (set (match_dup 5)
1547         (and:VF (match_dup 3)
1548                 (match_operand:VF 2 "nonimmediate_operand" "")))
1549    (set (match_operand:VF 0 "register_operand" "")
1550         (ior:VF (match_dup 4) (match_dup 5)))]
1551   "TARGET_SSE"
1552 {
1553   operands[3] = ix86_build_signbit_mask (<MODE>mode, 1, 0);
1554
1555   operands[4] = gen_reg_rtx (<MODE>mode);
1556   operands[5] = gen_reg_rtx (<MODE>mode);
1557 })
1558
1559 ;; Also define scalar versions.  These are used for abs, neg, and
1560 ;; conditional move.  Using subregs into vector modes causes register
1561 ;; allocation lossage.  These patterns do not allow memory operands
1562 ;; because the native instructions read the full 128-bits.
1563
1564 (define_insn "*andnot<mode>3"
1565   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
1566         (and:MODEF
1567           (not:MODEF
1568             (match_operand:MODEF 1 "register_operand" "0,x"))
1569             (match_operand:MODEF 2 "register_operand" "x,x")))]
1570   "SSE_FLOAT_MODE_P (<MODE>mode)"
1571 {
1572   static char buf[32];
1573   const char *insn;
1574   const char *suffix
1575     = TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL ? "ps" : "<ssevecmodesuffix>";
1576
1577   switch (which_alternative)
1578     {
1579     case 0:
1580       insn = "andn%s\t{%%2, %%0|%%0, %%2}";
1581       break;
1582     case 1:
1583       insn = "vandn%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
1584       break;
1585     default:
1586       gcc_unreachable ();
1587     }
1588
1589   snprintf (buf, sizeof (buf), insn, suffix);
1590   return buf;
1591 }
1592   [(set_attr "isa" "noavx,avx")
1593    (set_attr "type" "sselog")
1594    (set_attr "prefix" "orig,vex")
1595    (set_attr "mode" "<ssevecmode>")])
1596
1597 (define_insn "*<code><mode>3"
1598   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
1599         (any_logic:MODEF
1600           (match_operand:MODEF 1 "register_operand" "%0,x")
1601           (match_operand:MODEF 2 "register_operand" "x,x")))]
1602   "SSE_FLOAT_MODE_P (<MODE>mode)"
1603 {
1604   static char buf[32];
1605   const char *insn;
1606   const char *suffix
1607     = TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL ? "ps" : "<ssevecmodesuffix>";
1608
1609   switch (which_alternative)
1610     {
1611     case 0:
1612       insn = "<logic>%s\t{%%2, %%0|%%0, %%2}";
1613       break;
1614     case 1:
1615       insn = "v<logic>%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
1616       break;
1617     default:
1618       gcc_unreachable ();
1619     }
1620
1621   snprintf (buf, sizeof (buf), insn, suffix);
1622   return buf;
1623 }
1624   [(set_attr "isa" "noavx,avx")
1625    (set_attr "type" "sselog")
1626    (set_attr "prefix" "orig,vex")
1627    (set_attr "mode" "<ssevecmode>")])
1628
1629 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1630 ;;
1631 ;; FMA4 floating point multiply/accumulate instructions.  This
1632 ;; includes the scalar version of the instructions as well as the
1633 ;; vector.
1634 ;;
1635 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1636
1637 ;; In order to match (*a * *b) + *c, particularly when vectorizing, allow
1638 ;; combine to generate a multiply/add with two memory references.  We then
1639 ;; split this insn, into loading up the destination register with one of the
1640 ;; memory operations.  If we don't manage to split the insn, reload will
1641 ;; generate the appropriate moves.  The reason this is needed, is that combine
1642 ;; has already folded one of the memory references into both the multiply and
1643 ;; add insns, and it can't generate a new pseudo.  I.e.:
1644 ;;      (set (reg1) (mem (addr1)))
1645 ;;      (set (reg2) (mult (reg1) (mem (addr2))))
1646 ;;      (set (reg3) (plus (reg2) (mem (addr3))))
1647 ;;
1648 ;; ??? This is historic, pre-dating the gimple fma transformation.
1649 ;; We could now properly represent that only one memory operand is
1650 ;; allowed and not be penalized during optimization.
1651
1652 ;; Intrinsic FMA operations.
1653
1654 ;; The standard names for fma is only available with SSE math enabled.
1655 (define_expand "fma<mode>4"
1656   [(set (match_operand:FMAMODE 0 "register_operand")
1657         (fma:FMAMODE
1658           (match_operand:FMAMODE 1 "nonimmediate_operand")
1659           (match_operand:FMAMODE 2 "nonimmediate_operand")
1660           (match_operand:FMAMODE 3 "nonimmediate_operand")))]
1661   "(TARGET_FMA || TARGET_FMA4) && TARGET_SSE_MATH")
1662
1663 (define_expand "fms<mode>4"
1664   [(set (match_operand:FMAMODE 0 "register_operand")
1665         (fma:FMAMODE
1666           (match_operand:FMAMODE 1 "nonimmediate_operand")
1667           (match_operand:FMAMODE 2 "nonimmediate_operand")
1668           (neg:FMAMODE (match_operand:FMAMODE 3 "nonimmediate_operand"))))]
1669   "(TARGET_FMA || TARGET_FMA4) && TARGET_SSE_MATH")
1670
1671 (define_expand "fnma<mode>4"
1672   [(set (match_operand:FMAMODE 0 "register_operand")
1673         (fma:FMAMODE
1674           (neg:FMAMODE (match_operand:FMAMODE 1 "nonimmediate_operand"))
1675           (match_operand:FMAMODE 2 "nonimmediate_operand")
1676           (match_operand:FMAMODE 3 "nonimmediate_operand")))]
1677   "(TARGET_FMA || TARGET_FMA4) && TARGET_SSE_MATH")
1678
1679 (define_expand "fnms<mode>4"
1680   [(set (match_operand:FMAMODE 0 "register_operand")
1681         (fma:FMAMODE
1682           (neg:FMAMODE (match_operand:FMAMODE 1 "nonimmediate_operand"))
1683           (match_operand:FMAMODE 2 "nonimmediate_operand")
1684           (neg:FMAMODE (match_operand:FMAMODE 3 "nonimmediate_operand"))))]
1685   "(TARGET_FMA || TARGET_FMA4) && TARGET_SSE_MATH")
1686
1687 ;; The builtin for fma4intrin.h is not constrained by SSE math enabled.
1688 (define_expand "fma4i_fmadd_<mode>"
1689   [(set (match_operand:FMAMODE 0 "register_operand")
1690         (fma:FMAMODE
1691           (match_operand:FMAMODE 1 "nonimmediate_operand")
1692           (match_operand:FMAMODE 2 "nonimmediate_operand")
1693           (match_operand:FMAMODE 3 "nonimmediate_operand")))]
1694   "TARGET_FMA || TARGET_FMA4")
1695
1696 (define_insn "*fma4i_fmadd_<mode>"
1697   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x")
1698         (fma:FMAMODE
1699           (match_operand:FMAMODE 1 "nonimmediate_operand" "%x,x")
1700           (match_operand:FMAMODE 2 "nonimmediate_operand" " x,m")
1701           (match_operand:FMAMODE 3 "nonimmediate_operand" "xm,x")))]
1702   "TARGET_FMA4"
1703   "vfmadd<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1704   [(set_attr "type" "ssemuladd")
1705    (set_attr "mode" "<MODE>")])
1706
1707 (define_insn "*fma4i_fmsub_<mode>"
1708   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x")
1709         (fma:FMAMODE
1710           (match_operand:FMAMODE 1 "nonimmediate_operand" "%x,x")
1711           (match_operand:FMAMODE 2 "nonimmediate_operand" " x,m")
1712           (neg:FMAMODE
1713             (match_operand:FMAMODE 3 "nonimmediate_operand" "xm,x"))))]
1714   "TARGET_FMA4"
1715   "vfmsub<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1716   [(set_attr "type" "ssemuladd")
1717    (set_attr "mode" "<MODE>")])
1718
1719 (define_insn "*fma4i_fnmadd_<mode>"
1720   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x")
1721         (fma:FMAMODE
1722           (neg:FMAMODE
1723             (match_operand:FMAMODE 1 "nonimmediate_operand" "%x,x"))
1724           (match_operand:FMAMODE   2 "nonimmediate_operand" " x,m")
1725           (match_operand:FMAMODE   3 "nonimmediate_operand" "xm,x")))]
1726   "TARGET_FMA4"
1727   "vfnmadd<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1728   [(set_attr "type" "ssemuladd")
1729    (set_attr "mode" "<MODE>")])
1730
1731 (define_insn "*fma4i_fnmsub_<mode>"
1732   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x")
1733         (fma:FMAMODE
1734           (neg:FMAMODE
1735             (match_operand:FMAMODE 1 "nonimmediate_operand" "%x,x"))
1736           (match_operand:FMAMODE   2 "nonimmediate_operand" " x,m")
1737           (neg:FMAMODE
1738             (match_operand:FMAMODE 3 "nonimmediate_operand" "xm,x"))))]
1739   "TARGET_FMA4"
1740   "vfnmsub<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1741   [(set_attr "type" "ssemuladd")
1742    (set_attr "mode" "<MODE>")])
1743
1744 ;; Scalar versions of the above.  Unlike ADDSS et al, these write the
1745 ;; entire destination register, with the high-order elements zeroed.
1746
1747 (define_expand "fma4i_vmfmadd_<mode>"
1748   [(set (match_operand:VF_128 0 "register_operand")
1749         (vec_merge:VF_128
1750           (fma:VF_128
1751             (match_operand:VF_128 1 "nonimmediate_operand")
1752             (match_operand:VF_128 2 "nonimmediate_operand")
1753             (match_operand:VF_128 3 "nonimmediate_operand"))
1754           (match_dup 4)
1755           (const_int 1)))]
1756   "TARGET_FMA4"
1757 {
1758   operands[4] = CONST0_RTX (<MODE>mode);
1759 })
1760
1761 (define_expand "fmai_vmfmadd_<mode>"
1762   [(set (match_operand:VF_128 0 "register_operand")
1763         (vec_merge:VF_128
1764           (fma:VF_128
1765             (match_operand:VF_128 1 "nonimmediate_operand")
1766             (match_operand:VF_128 2 "nonimmediate_operand")
1767             (match_operand:VF_128 3 "nonimmediate_operand"))
1768           (match_dup 0)
1769           (const_int 1)))]
1770   "TARGET_FMA")
1771
1772 (define_insn "*fmai_fmadd_<mode>"
1773   [(set (match_operand:VF_128 0 "register_operand" "=x,x,x")
1774         (vec_merge:VF_128
1775           (fma:VF_128
1776             (match_operand:VF_128 1 "nonimmediate_operand" "%0, 0,x")
1777             (match_operand:VF_128 2 "nonimmediate_operand" "xm, x,xm")
1778             (match_operand:VF_128 3 "nonimmediate_operand" " x,xm,0"))
1779           (match_dup 0)
1780           (const_int 1)))]
1781   "TARGET_FMA"
1782   "@
1783    vfmadd132<ssescalarmodesuffix>\t{%2, %3, %0|%0, %3, %2}
1784    vfmadd213<ssescalarmodesuffix>\t{%3, %2, %0|%0, %2, %3}
1785    vfmadd231<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1786   [(set_attr "type" "ssemuladd")
1787    (set_attr "mode" "<MODE>")])
1788
1789 (define_insn "*fmai_fmsub_<mode>"
1790   [(set (match_operand:VF_128 0 "register_operand" "=x,x,x")
1791         (vec_merge:VF_128
1792           (fma:VF_128
1793             (match_operand:VF_128   1 "nonimmediate_operand" "%0, 0,x")
1794             (match_operand:VF_128   2 "nonimmediate_operand" "xm, x,xm")
1795             (neg:VF_128
1796               (match_operand:VF_128 3 "nonimmediate_operand" " x,xm,0")))
1797           (match_dup 0)
1798           (const_int 1)))]
1799   "TARGET_FMA"
1800   "@
1801    vfmsub132<ssescalarmodesuffix>\t{%2, %3, %0|%0, %3, %2}
1802    vfmsub213<ssescalarmodesuffix>\t{%3, %2, %0|%0, %2, %3}
1803    vfmsub231<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1804   [(set_attr "type" "ssemuladd")
1805    (set_attr "mode" "<MODE>")])
1806
1807 (define_insn "*fmai_fnmadd_<mode>"
1808   [(set (match_operand:VF_128 0 "register_operand" "=x,x,x")
1809         (vec_merge:VF_128
1810           (fma:VF_128
1811             (neg:VF_128
1812               (match_operand:VF_128 1 "nonimmediate_operand" "%0, 0,x"))
1813             (match_operand:VF_128   2 "nonimmediate_operand" "xm, x,xm")
1814             (match_operand:VF_128   3 "nonimmediate_operand" " x,xm,0"))
1815           (match_dup 0)
1816           (const_int 1)))]
1817   "TARGET_FMA"
1818   "@
1819    vfnmadd132<ssescalarmodesuffix>\t{%2, %3, %0|%0, %3, %2}
1820    vfnmadd213<ssescalarmodesuffix>\t{%3, %2, %0|%0, %2, %3}
1821    vfnmadd231<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1822   [(set_attr "type" "ssemuladd")
1823    (set_attr "mode" "<MODE>")])
1824
1825 (define_insn "*fmai_fnmsub_<mode>"
1826   [(set (match_operand:VF_128 0 "register_operand" "=x,x,x")
1827         (vec_merge:VF_128
1828           (fma:VF_128
1829             (neg:VF_128
1830               (match_operand:VF_128 1 "nonimmediate_operand" "%0, 0,x"))
1831             (match_operand:VF_128   2 "nonimmediate_operand" "xm, x,xm")
1832             (neg:VF_128
1833               (match_operand:VF_128 3 "nonimmediate_operand" " x,xm,0")))
1834           (match_dup 0)
1835           (const_int 1)))]
1836   "TARGET_FMA"
1837   "@
1838    vfnmsub132<ssescalarmodesuffix>\t{%2, %3, %0|%0, %3, %2}
1839    vfnmsub213<ssescalarmodesuffix>\t{%3, %2, %0|%0, %2, %3}
1840    vfnmsub231<ssescalarmodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1841   [(set_attr "type" "ssemuladd")
1842    (set_attr "mode" "<MODE>")])
1843
1844 (define_insn "*fma4i_vmfmadd_<mode>"
1845   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
1846         (vec_merge:VF_128
1847           (fma:VF_128
1848             (match_operand:VF_128 1 "nonimmediate_operand" "%x,x")
1849             (match_operand:VF_128 2 "nonimmediate_operand" " x,m")
1850             (match_operand:VF_128 3 "nonimmediate_operand" "xm,x"))
1851           (match_operand:VF_128 4 "const0_operand" "")
1852           (const_int 1)))]
1853   "TARGET_FMA4"
1854   "vfmadd<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1855   [(set_attr "type" "ssemuladd")
1856    (set_attr "mode" "<MODE>")])
1857
1858 (define_insn "*fma4i_vmfmsub_<mode>"
1859   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
1860         (vec_merge:VF_128
1861           (fma:VF_128
1862             (match_operand:VF_128 1 "nonimmediate_operand" "%x,x")
1863             (match_operand:VF_128 2 "nonimmediate_operand" " x,m")
1864             (neg:VF_128
1865               (match_operand:VF_128 3 "nonimmediate_operand" "xm,x")))
1866           (match_operand:VF_128 4 "const0_operand" "")
1867           (const_int 1)))]
1868   "TARGET_FMA4"
1869   "vfmsub<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1870   [(set_attr "type" "ssemuladd")
1871    (set_attr "mode" "<MODE>")])
1872
1873 (define_insn "*fma4i_vmfnmadd_<mode>"
1874   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
1875         (vec_merge:VF_128
1876           (fma:VF_128
1877             (neg:VF_128
1878               (match_operand:VF_128 1 "nonimmediate_operand" "%x,x"))
1879             (match_operand:VF_128   2 "nonimmediate_operand" " x,m")
1880             (match_operand:VF_128   3 "nonimmediate_operand" "xm,x"))
1881           (match_operand:VF_128 4 "const0_operand" "")
1882           (const_int 1)))]
1883   "TARGET_FMA4"
1884   "vfnmadd<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1885   [(set_attr "type" "ssemuladd")
1886    (set_attr "mode" "<MODE>")])
1887
1888 (define_insn "*fma4i_vmfnmsub_<mode>"
1889   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
1890         (vec_merge:VF_128
1891           (fma:VF_128
1892             (neg:VF_128
1893               (match_operand:VF_128 1 "nonimmediate_operand" "%x,x"))
1894             (match_operand:VF_128   2 "nonimmediate_operand" " x,m")
1895             (neg:VF_128
1896               (match_operand:VF_128   3 "nonimmediate_operand" "xm,x")))
1897           (match_operand:VF_128 4 "const0_operand" "")
1898           (const_int 1)))]
1899   "TARGET_FMA4"
1900   "vfnmsub<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1901   [(set_attr "type" "ssemuladd")
1902    (set_attr "mode" "<MODE>")])
1903
1904 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1905 ;;
1906 ;; FMA4 Parallel floating point multiply addsub and subadd operations.
1907 ;;
1908 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1909
1910 ;; It would be possible to represent these without the UNSPEC as
1911 ;;
1912 ;; (vec_merge
1913 ;;   (fma op1 op2 op3)
1914 ;;   (fma op1 op2 (neg op3))
1915 ;;   (merge-const))
1916 ;;
1917 ;; But this doesn't seem useful in practice.
1918
1919 (define_expand "fmaddsub_<mode>"
1920   [(set (match_operand:VF 0 "register_operand")
1921         (unspec:VF
1922           [(match_operand:VF 1 "nonimmediate_operand")
1923            (match_operand:VF 2 "nonimmediate_operand")
1924            (match_operand:VF 3 "nonimmediate_operand")]
1925           UNSPEC_FMADDSUB))]
1926   "TARGET_FMA || TARGET_FMA4")
1927
1928 (define_insn "*fma4_fmaddsub_<mode>"
1929   [(set (match_operand:VF 0 "register_operand" "=x,x")
1930         (unspec:VF
1931           [(match_operand:VF 1 "nonimmediate_operand" "%x,x")
1932            (match_operand:VF 2 "nonimmediate_operand" " x,m")
1933            (match_operand:VF 3 "nonimmediate_operand" "xm,x")]
1934           UNSPEC_FMADDSUB))]
1935   "TARGET_FMA4"
1936   "vfmaddsub<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1937   [(set_attr "type" "ssemuladd")
1938    (set_attr "mode" "<MODE>")])
1939
1940 (define_insn "*fma4_fmsubadd_<mode>"
1941   [(set (match_operand:VF 0 "register_operand" "=x,x")
1942         (unspec:VF
1943           [(match_operand:VF 1 "nonimmediate_operand" "%x,x")
1944            (match_operand:VF 2 "nonimmediate_operand" " x,m")
1945            (neg:VF
1946              (match_operand:VF 3 "nonimmediate_operand" "xm,x"))]
1947           UNSPEC_FMADDSUB))]
1948   "TARGET_FMA4"
1949   "vfmsubadd<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
1950   [(set_attr "type" "ssemuladd")
1951    (set_attr "mode" "<MODE>")])
1952
1953 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1954 ;;
1955 ;; FMA3 floating point multiply/accumulate instructions.
1956 ;;
1957 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1958
1959 (define_insn "*fma_fmadd_<mode>"
1960   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x,x")
1961         (fma:FMAMODE
1962           (match_operand:FMAMODE 1 "nonimmediate_operand" "%0, 0,x")
1963           (match_operand:FMAMODE 2 "nonimmediate_operand" "xm, x,xm")
1964           (match_operand:FMAMODE 3 "nonimmediate_operand" " x,xm,0")))]
1965   "TARGET_FMA"
1966   "@
1967    vfmadd132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
1968    vfmadd213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
1969    vfmadd231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1970   [(set_attr "type" "ssemuladd")
1971    (set_attr "mode" "<MODE>")])
1972
1973 (define_insn "*fma_fmsub_<mode>"
1974   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x,x")
1975         (fma:FMAMODE
1976           (match_operand:FMAMODE   1 "nonimmediate_operand" "%0, 0,x")
1977           (match_operand:FMAMODE   2 "nonimmediate_operand" "xm, x,xm")
1978           (neg:FMAMODE
1979             (match_operand:FMAMODE 3 "nonimmediate_operand" " x,xm,0"))))]
1980   "TARGET_FMA"
1981   "@
1982    vfmsub132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
1983    vfmsub213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
1984    vfmsub231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
1985   [(set_attr "type" "ssemuladd")
1986    (set_attr "mode" "<MODE>")])
1987
1988 (define_insn "*fma_fnmadd_<mode>"
1989   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x,x")
1990         (fma:FMAMODE
1991           (neg:FMAMODE
1992             (match_operand:FMAMODE 1 "nonimmediate_operand" "%0, 0,x"))
1993           (match_operand:FMAMODE   2 "nonimmediate_operand" "xm, x,xm")
1994           (match_operand:FMAMODE   3 "nonimmediate_operand" " x,xm,0")))]
1995   "TARGET_FMA"
1996   "@
1997    vfnmadd132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
1998    vfnmadd213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
1999    vfnmadd231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
2000   [(set_attr "type" "ssemuladd")
2001    (set_attr "mode" "<MODE>")])
2002
2003 (define_insn "*fma_fnmsub_<mode>"
2004   [(set (match_operand:FMAMODE 0 "register_operand" "=x,x,x")
2005         (fma:FMAMODE
2006           (neg:FMAMODE
2007             (match_operand:FMAMODE 1 "nonimmediate_operand" "%0, 0,x"))
2008           (match_operand:FMAMODE   2 "nonimmediate_operand" "xm, x,xm")
2009           (neg:FMAMODE
2010             (match_operand:FMAMODE 3 "nonimmediate_operand" " x,xm,0"))))]
2011   "TARGET_FMA"
2012   "@
2013    vfnmsub132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
2014    vfnmsub213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
2015    vfnmsub231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
2016   [(set_attr "type" "ssemuladd")
2017    (set_attr "mode" "<MODE>")])
2018
2019 (define_insn "*fma_fmaddsub_<mode>"
2020   [(set (match_operand:VF 0 "register_operand" "=x,x,x")
2021         (unspec:VF
2022           [(match_operand:VF 1 "nonimmediate_operand" "%0, 0,x")
2023            (match_operand:VF 2 "nonimmediate_operand" "xm, x,xm")
2024            (match_operand:VF 3 "nonimmediate_operand" " x,xm,0")]
2025           UNSPEC_FMADDSUB))]
2026   "TARGET_FMA"
2027   "@
2028    vfmaddsub132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
2029    vfmaddsub213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
2030    vfmaddsub231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
2031   [(set_attr "type" "ssemuladd")
2032    (set_attr "mode" "<MODE>")])
2033
2034 (define_insn "*fma_fmsubadd_<mode>"
2035   [(set (match_operand:VF 0 "register_operand" "=x,x,x")
2036         (unspec:VF
2037           [(match_operand:VF   1 "nonimmediate_operand" "%0, 0,x")
2038            (match_operand:VF   2 "nonimmediate_operand" "xm, x,xm")
2039            (neg:VF
2040              (match_operand:VF 3 "nonimmediate_operand" " x,xm,0"))]
2041           UNSPEC_FMADDSUB))]
2042   "TARGET_FMA"
2043   "@
2044    vfmsubadd132<ssemodesuffix>\t{%2, %3, %0|%0, %3, %2}
2045    vfmsubadd213<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
2046    vfmsubadd231<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
2047   [(set_attr "type" "ssemuladd")
2048    (set_attr "mode" "<MODE>")])
2049
2050 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2051 ;;
2052 ;; Parallel single-precision floating point conversion operations
2053 ;;
2054 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2055
2056 (define_insn "sse_cvtpi2ps"
2057   [(set (match_operand:V4SF 0 "register_operand" "=x")
2058         (vec_merge:V4SF
2059           (vec_duplicate:V4SF
2060             (float:V2SF (match_operand:V2SI 2 "nonimmediate_operand" "ym")))
2061           (match_operand:V4SF 1 "register_operand" "0")
2062           (const_int 3)))]
2063   "TARGET_SSE"
2064   "cvtpi2ps\t{%2, %0|%0, %2}"
2065   [(set_attr "type" "ssecvt")
2066    (set_attr "mode" "V4SF")])
2067
2068 (define_insn "sse_cvtps2pi"
2069   [(set (match_operand:V2SI 0 "register_operand" "=y")
2070         (vec_select:V2SI
2071           (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
2072                        UNSPEC_FIX_NOTRUNC)
2073           (parallel [(const_int 0) (const_int 1)])))]
2074   "TARGET_SSE"
2075   "cvtps2pi\t{%1, %0|%0, %1}"
2076   [(set_attr "type" "ssecvt")
2077    (set_attr "unit" "mmx")
2078    (set_attr "mode" "DI")])
2079
2080 (define_insn "sse_cvttps2pi"
2081   [(set (match_operand:V2SI 0 "register_operand" "=y")
2082         (vec_select:V2SI
2083           (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm"))
2084           (parallel [(const_int 0) (const_int 1)])))]
2085   "TARGET_SSE"
2086   "cvttps2pi\t{%1, %0|%0, %1}"
2087   [(set_attr "type" "ssecvt")
2088    (set_attr "unit" "mmx")
2089    (set_attr "prefix_rep" "0")
2090    (set_attr "mode" "SF")])
2091
2092 (define_insn "sse_cvtsi2ss"
2093   [(set (match_operand:V4SF 0 "register_operand" "=x,x,x")
2094         (vec_merge:V4SF
2095           (vec_duplicate:V4SF
2096             (float:SF (match_operand:SI 2 "nonimmediate_operand" "r,m,rm")))
2097           (match_operand:V4SF 1 "register_operand" "0,0,x")
2098           (const_int 1)))]
2099   "TARGET_SSE"
2100   "@
2101    cvtsi2ss\t{%2, %0|%0, %2}
2102    cvtsi2ss\t{%2, %0|%0, %2}
2103    vcvtsi2ss\t{%2, %1, %0|%0, %1, %2}"
2104   [(set_attr "isa" "noavx,noavx,avx")
2105    (set_attr "type" "sseicvt")
2106    (set_attr "athlon_decode" "vector,double,*")
2107    (set_attr "amdfam10_decode" "vector,double,*")
2108    (set_attr "bdver1_decode" "double,direct,*")
2109    (set_attr "prefix" "orig,orig,vex")
2110    (set_attr "mode" "SF")])
2111
2112 (define_insn "sse_cvtsi2ssq"
2113   [(set (match_operand:V4SF 0 "register_operand" "=x,x,x")
2114         (vec_merge:V4SF
2115           (vec_duplicate:V4SF
2116             (float:SF (match_operand:DI 2 "nonimmediate_operand" "r,m,rm")))
2117           (match_operand:V4SF 1 "register_operand" "0,0,x")
2118           (const_int 1)))]
2119   "TARGET_SSE && TARGET_64BIT"
2120   "@
2121    cvtsi2ssq\t{%2, %0|%0, %2}
2122    cvtsi2ssq\t{%2, %0|%0, %2}
2123    vcvtsi2ssq\t{%2, %1, %0|%0, %1, %2}"
2124   [(set_attr "isa" "noavx,noavx,avx")
2125    (set_attr "type" "sseicvt")
2126    (set_attr "athlon_decode" "vector,double,*")
2127    (set_attr "amdfam10_decode" "vector,double,*")
2128    (set_attr "bdver1_decode" "double,direct,*")
2129    (set_attr "length_vex" "*,*,4")
2130    (set_attr "prefix_rex" "1,1,*")
2131    (set_attr "prefix" "orig,orig,vex")
2132    (set_attr "mode" "SF")])
2133
2134 (define_insn "sse_cvtss2si"
2135   [(set (match_operand:SI 0 "register_operand" "=r,r")
2136         (unspec:SI
2137           [(vec_select:SF
2138              (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2139              (parallel [(const_int 0)]))]
2140           UNSPEC_FIX_NOTRUNC))]
2141   "TARGET_SSE"
2142   "%vcvtss2si\t{%1, %0|%0, %1}"
2143   [(set_attr "type" "sseicvt")
2144    (set_attr "athlon_decode" "double,vector")
2145    (set_attr "bdver1_decode" "double,double")
2146    (set_attr "prefix_rep" "1")
2147    (set_attr "prefix" "maybe_vex")
2148    (set_attr "mode" "SI")])
2149
2150 (define_insn "sse_cvtss2si_2"
2151   [(set (match_operand:SI 0 "register_operand" "=r,r")
2152         (unspec:SI [(match_operand:SF 1 "nonimmediate_operand" "x,m")]
2153                    UNSPEC_FIX_NOTRUNC))]
2154   "TARGET_SSE"
2155   "%vcvtss2si\t{%1, %0|%0, %1}"
2156   [(set_attr "type" "sseicvt")
2157    (set_attr "athlon_decode" "double,vector")
2158    (set_attr "amdfam10_decode" "double,double")
2159    (set_attr "bdver1_decode" "double,double")
2160    (set_attr "prefix_rep" "1")
2161    (set_attr "prefix" "maybe_vex")
2162    (set_attr "mode" "SI")])
2163
2164 (define_insn "sse_cvtss2siq"
2165   [(set (match_operand:DI 0 "register_operand" "=r,r")
2166         (unspec:DI
2167           [(vec_select:SF
2168              (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2169              (parallel [(const_int 0)]))]
2170           UNSPEC_FIX_NOTRUNC))]
2171   "TARGET_SSE && TARGET_64BIT"
2172   "%vcvtss2si{q}\t{%1, %0|%0, %1}"
2173   [(set_attr "type" "sseicvt")
2174    (set_attr "athlon_decode" "double,vector")
2175    (set_attr "bdver1_decode" "double,double")
2176    (set_attr "prefix_rep" "1")
2177    (set_attr "prefix" "maybe_vex")
2178    (set_attr "mode" "DI")])
2179
2180 (define_insn "sse_cvtss2siq_2"
2181   [(set (match_operand:DI 0 "register_operand" "=r,r")
2182         (unspec:DI [(match_operand:SF 1 "nonimmediate_operand" "x,m")]
2183                    UNSPEC_FIX_NOTRUNC))]
2184   "TARGET_SSE && TARGET_64BIT"
2185   "%vcvtss2si{q}\t{%1, %0|%0, %1}"
2186   [(set_attr "type" "sseicvt")
2187    (set_attr "athlon_decode" "double,vector")
2188    (set_attr "amdfam10_decode" "double,double")
2189    (set_attr "bdver1_decode" "double,double")
2190    (set_attr "prefix_rep" "1")
2191    (set_attr "prefix" "maybe_vex")
2192    (set_attr "mode" "DI")])
2193
2194 (define_insn "sse_cvttss2si"
2195   [(set (match_operand:SI 0 "register_operand" "=r,r")
2196         (fix:SI
2197           (vec_select:SF
2198             (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2199             (parallel [(const_int 0)]))))]
2200   "TARGET_SSE"
2201   "%vcvttss2si\t{%1, %0|%0, %1}"
2202   [(set_attr "type" "sseicvt")
2203    (set_attr "athlon_decode" "double,vector")
2204    (set_attr "amdfam10_decode" "double,double")
2205    (set_attr "bdver1_decode" "double,double")
2206    (set_attr "prefix_rep" "1")
2207    (set_attr "prefix" "maybe_vex")
2208    (set_attr "mode" "SI")])
2209
2210 (define_insn "sse_cvttss2siq"
2211   [(set (match_operand:DI 0 "register_operand" "=r,r")
2212         (fix:DI
2213           (vec_select:SF
2214             (match_operand:V4SF 1 "nonimmediate_operand" "x,m")
2215             (parallel [(const_int 0)]))))]
2216   "TARGET_SSE && TARGET_64BIT"
2217   "%vcvttss2si{q}\t{%1, %0|%0, %1}"
2218   [(set_attr "type" "sseicvt")
2219    (set_attr "athlon_decode" "double,vector")
2220    (set_attr "amdfam10_decode" "double,double")
2221    (set_attr "bdver1_decode" "double,double")
2222    (set_attr "prefix_rep" "1")
2223    (set_attr "prefix" "maybe_vex")
2224    (set_attr "mode" "DI")])
2225
2226 (define_insn "float<sseintvecmodelower><mode>2"
2227   [(set (match_operand:VF1 0 "register_operand" "=x")
2228         (float:VF1
2229           (match_operand:<sseintvecmode> 1 "nonimmediate_operand" "xm")))]
2230   "TARGET_SSE2"
2231   "%vcvtdq2ps\t{%1, %0|%0, %1}"
2232   [(set_attr "type" "ssecvt")
2233    (set_attr "prefix" "maybe_vex")
2234    (set_attr "mode" "<sseinsnmode>")])
2235
2236 (define_expand "floatuns<sseintvecmodelower><mode>2"
2237   [(match_operand:VF1 0 "register_operand" "")
2238    (match_operand:<sseintvecmode> 1 "register_operand" "")]
2239   "TARGET_SSE2 && (<MODE>mode == V4SFmode || TARGET_AVX2)"
2240 {
2241   ix86_expand_vector_convert_uns_vsivsf (operands[0], operands[1]);
2242   DONE;
2243 })
2244
2245 (define_insn "avx_cvtps2dq256"
2246   [(set (match_operand:V8SI 0 "register_operand" "=x")
2247         (unspec:V8SI [(match_operand:V8SF 1 "nonimmediate_operand" "xm")]
2248                      UNSPEC_FIX_NOTRUNC))]
2249   "TARGET_AVX"
2250   "vcvtps2dq\t{%1, %0|%0, %1}"
2251   [(set_attr "type" "ssecvt")
2252    (set_attr "prefix" "vex")
2253    (set_attr "mode" "OI")])
2254
2255 (define_insn "sse2_cvtps2dq"
2256   [(set (match_operand:V4SI 0 "register_operand" "=x")
2257         (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
2258                      UNSPEC_FIX_NOTRUNC))]
2259   "TARGET_SSE2"
2260   "%vcvtps2dq\t{%1, %0|%0, %1}"
2261   [(set_attr "type" "ssecvt")
2262    (set (attr "prefix_data16")
2263      (if_then_else
2264        (match_test "TARGET_AVX")
2265      (const_string "*")
2266      (const_string "1")))
2267    (set_attr "prefix" "maybe_vex")
2268    (set_attr "mode" "TI")])
2269
2270 (define_insn "fix_truncv8sfv8si2"
2271   [(set (match_operand:V8SI 0 "register_operand" "=x")
2272         (fix:V8SI (match_operand:V8SF 1 "nonimmediate_operand" "xm")))]
2273   "TARGET_AVX"
2274   "vcvttps2dq\t{%1, %0|%0, %1}"
2275   [(set_attr "type" "ssecvt")
2276    (set_attr "prefix" "vex")
2277    (set_attr "mode" "OI")])
2278
2279 (define_insn "fix_truncv4sfv4si2"
2280   [(set (match_operand:V4SI 0 "register_operand" "=x")
2281         (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
2282   "TARGET_SSE2"
2283   "%vcvttps2dq\t{%1, %0|%0, %1}"
2284   [(set_attr "type" "ssecvt")
2285    (set (attr "prefix_rep")
2286      (if_then_else
2287        (match_test "TARGET_AVX")
2288      (const_string "*")
2289      (const_string "1")))
2290    (set (attr "prefix_data16")
2291      (if_then_else
2292        (match_test "TARGET_AVX")
2293      (const_string "*")
2294      (const_string "0")))
2295    (set_attr "prefix_data16" "0")
2296    (set_attr "prefix" "maybe_vex")
2297    (set_attr "mode" "TI")])
2298
2299 (define_expand "fixuns_trunc<mode><sseintvecmodelower>2"
2300   [(match_operand:<sseintvecmode> 0 "register_operand" "")
2301    (match_operand:VF1 1 "register_operand" "")]
2302   "TARGET_SSE2"
2303 {
2304   rtx tmp[3];
2305   tmp[0] = ix86_expand_adjust_ufix_to_sfix_si (operands[1], &tmp[2]);
2306   tmp[1] = gen_reg_rtx (<sseintvecmode>mode);
2307   emit_insn (gen_fix_trunc<mode><sseintvecmodelower>2 (tmp[1], tmp[0]));
2308   emit_insn (gen_xor<sseintvecmodelower>3 (operands[0], tmp[1], tmp[2]));
2309   DONE;
2310 })
2311
2312 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2313 ;;
2314 ;; Parallel double-precision floating point conversion operations
2315 ;;
2316 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2317
2318 (define_insn "sse2_cvtpi2pd"
2319   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
2320         (float:V2DF (match_operand:V2SI 1 "nonimmediate_operand" "y,m")))]
2321   "TARGET_SSE2"
2322   "cvtpi2pd\t{%1, %0|%0, %1}"
2323   [(set_attr "type" "ssecvt")
2324    (set_attr "unit" "mmx,*")
2325    (set_attr "prefix_data16" "1,*")
2326    (set_attr "mode" "V2DF")])
2327
2328 (define_insn "sse2_cvtpd2pi"
2329   [(set (match_operand:V2SI 0 "register_operand" "=y")
2330         (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
2331                      UNSPEC_FIX_NOTRUNC))]
2332   "TARGET_SSE2"
2333   "cvtpd2pi\t{%1, %0|%0, %1}"
2334   [(set_attr "type" "ssecvt")
2335    (set_attr "unit" "mmx")
2336    (set_attr "bdver1_decode" "double")
2337    (set_attr "prefix_data16" "1")
2338    (set_attr "mode" "DI")])
2339
2340 (define_insn "sse2_cvttpd2pi"
2341   [(set (match_operand:V2SI 0 "register_operand" "=y")
2342         (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm")))]
2343   "TARGET_SSE2"
2344   "cvttpd2pi\t{%1, %0|%0, %1}"
2345   [(set_attr "type" "ssecvt")
2346    (set_attr "unit" "mmx")
2347    (set_attr "bdver1_decode" "double")
2348    (set_attr "prefix_data16" "1")
2349    (set_attr "mode" "TI")])
2350
2351 (define_insn "sse2_cvtsi2sd"
2352   [(set (match_operand:V2DF 0 "register_operand" "=x,x,x")
2353         (vec_merge:V2DF
2354           (vec_duplicate:V2DF
2355             (float:DF (match_operand:SI 2 "nonimmediate_operand" "r,m,rm")))
2356           (match_operand:V2DF 1 "register_operand" "0,0,x")
2357           (const_int 1)))]
2358   "TARGET_SSE2"
2359   "@
2360    cvtsi2sd\t{%2, %0|%0, %2}
2361    cvtsi2sd\t{%2, %0|%0, %2}
2362    vcvtsi2sd\t{%2, %1, %0|%0, %1, %2}"
2363   [(set_attr "isa" "noavx,noavx,avx")
2364    (set_attr "type" "sseicvt")
2365    (set_attr "athlon_decode" "double,direct,*")
2366    (set_attr "amdfam10_decode" "vector,double,*")
2367    (set_attr "bdver1_decode" "double,direct,*")
2368    (set_attr "prefix" "orig,orig,vex")
2369    (set_attr "mode" "DF")])
2370
2371 (define_insn "sse2_cvtsi2sdq"
2372   [(set (match_operand:V2DF 0 "register_operand" "=x,x,x")
2373         (vec_merge:V2DF
2374           (vec_duplicate:V2DF
2375             (float:DF (match_operand:DI 2 "nonimmediate_operand" "r,m,rm")))
2376           (match_operand:V2DF 1 "register_operand" "0,0,x")
2377           (const_int 1)))]
2378   "TARGET_SSE2 && TARGET_64BIT"
2379   "@
2380    cvtsi2sdq\t{%2, %0|%0, %2}
2381    cvtsi2sdq\t{%2, %0|%0, %2}
2382    vcvtsi2sdq\t{%2, %1, %0|%0, %1, %2}"
2383   [(set_attr "isa" "noavx,noavx,avx")
2384    (set_attr "type" "sseicvt")
2385    (set_attr "athlon_decode" "double,direct,*")
2386    (set_attr "amdfam10_decode" "vector,double,*")
2387    (set_attr "bdver1_decode" "double,direct,*")
2388    (set_attr "length_vex" "*,*,4")
2389    (set_attr "prefix_rex" "1,1,*")
2390    (set_attr "prefix" "orig,orig,vex")
2391    (set_attr "mode" "DF")])
2392
2393 (define_insn "sse2_cvtsd2si"
2394   [(set (match_operand:SI 0 "register_operand" "=r,r")
2395         (unspec:SI
2396           [(vec_select:DF
2397              (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2398              (parallel [(const_int 0)]))]
2399           UNSPEC_FIX_NOTRUNC))]
2400   "TARGET_SSE2"
2401   "%vcvtsd2si\t{%1, %0|%0, %1}"
2402   [(set_attr "type" "sseicvt")
2403    (set_attr "athlon_decode" "double,vector")
2404    (set_attr "bdver1_decode" "double,double")
2405    (set_attr "prefix_rep" "1")
2406    (set_attr "prefix" "maybe_vex")
2407    (set_attr "mode" "SI")])
2408
2409 (define_insn "sse2_cvtsd2si_2"
2410   [(set (match_operand:SI 0 "register_operand" "=r,r")
2411         (unspec:SI [(match_operand:DF 1 "nonimmediate_operand" "x,m")]
2412                    UNSPEC_FIX_NOTRUNC))]
2413   "TARGET_SSE2"
2414   "%vcvtsd2si\t{%1, %0|%0, %1}"
2415   [(set_attr "type" "sseicvt")
2416    (set_attr "athlon_decode" "double,vector")
2417    (set_attr "amdfam10_decode" "double,double")
2418    (set_attr "bdver1_decode" "double,double")
2419    (set_attr "prefix_rep" "1")
2420    (set_attr "prefix" "maybe_vex")
2421    (set_attr "mode" "SI")])
2422
2423 (define_insn "sse2_cvtsd2siq"
2424   [(set (match_operand:DI 0 "register_operand" "=r,r")
2425         (unspec:DI
2426           [(vec_select:DF
2427              (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2428              (parallel [(const_int 0)]))]
2429           UNSPEC_FIX_NOTRUNC))]
2430   "TARGET_SSE2 && TARGET_64BIT"
2431   "%vcvtsd2si{q}\t{%1, %0|%0, %1}"
2432   [(set_attr "type" "sseicvt")
2433    (set_attr "athlon_decode" "double,vector")
2434    (set_attr "bdver1_decode" "double,double")
2435    (set_attr "prefix_rep" "1")
2436    (set_attr "prefix" "maybe_vex")
2437    (set_attr "mode" "DI")])
2438
2439 (define_insn "sse2_cvtsd2siq_2"
2440   [(set (match_operand:DI 0 "register_operand" "=r,r")
2441         (unspec:DI [(match_operand:DF 1 "nonimmediate_operand" "x,m")]
2442                    UNSPEC_FIX_NOTRUNC))]
2443   "TARGET_SSE2 && TARGET_64BIT"
2444   "%vcvtsd2si{q}\t{%1, %0|%0, %1}"
2445   [(set_attr "type" "sseicvt")
2446    (set_attr "athlon_decode" "double,vector")
2447    (set_attr "amdfam10_decode" "double,double")
2448    (set_attr "bdver1_decode" "double,double")
2449    (set_attr "prefix_rep" "1")
2450    (set_attr "prefix" "maybe_vex")
2451    (set_attr "mode" "DI")])
2452
2453 (define_insn "sse2_cvttsd2si"
2454   [(set (match_operand:SI 0 "register_operand" "=r,r")
2455         (fix:SI
2456           (vec_select:DF
2457             (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2458             (parallel [(const_int 0)]))))]
2459   "TARGET_SSE2"
2460   "%vcvttsd2si\t{%1, %0|%0, %1}"
2461   [(set_attr "type" "sseicvt")
2462    (set_attr "athlon_decode" "double,vector")
2463    (set_attr "amdfam10_decode" "double,double")
2464    (set_attr "bdver1_decode" "double,double")
2465    (set_attr "prefix_rep" "1")
2466    (set_attr "prefix" "maybe_vex")
2467    (set_attr "mode" "SI")])
2468
2469 (define_insn "sse2_cvttsd2siq"
2470   [(set (match_operand:DI 0 "register_operand" "=r,r")
2471         (fix:DI
2472           (vec_select:DF
2473             (match_operand:V2DF 1 "nonimmediate_operand" "x,m")
2474             (parallel [(const_int 0)]))))]
2475   "TARGET_SSE2 && TARGET_64BIT"
2476   "%vcvttsd2si{q}\t{%1, %0|%0, %1}"
2477   [(set_attr "type" "sseicvt")
2478    (set_attr "athlon_decode" "double,vector")
2479    (set_attr "amdfam10_decode" "double,double")
2480    (set_attr "bdver1_decode" "double,double")
2481    (set_attr "prefix_rep" "1")
2482    (set_attr "prefix" "maybe_vex")
2483    (set_attr "mode" "DI")])
2484
2485 (define_insn "floatv4siv4df2"
2486   [(set (match_operand:V4DF 0 "register_operand" "=x")
2487         (float:V4DF (match_operand:V4SI 1 "nonimmediate_operand" "xm")))]
2488   "TARGET_AVX"
2489   "vcvtdq2pd\t{%1, %0|%0, %1}"
2490   [(set_attr "type" "ssecvt")
2491    (set_attr "prefix" "vex")
2492    (set_attr "mode" "V4DF")])
2493
2494 (define_insn "avx_cvtdq2pd256_2"
2495   [(set (match_operand:V4DF 0 "register_operand" "=x")
2496         (float:V4DF
2497           (vec_select:V4SI
2498             (match_operand:V8SI 1 "nonimmediate_operand" "xm")
2499             (parallel [(const_int 0) (const_int 1)
2500                        (const_int 2) (const_int 3)]))))]
2501   "TARGET_AVX"
2502   "vcvtdq2pd\t{%x1, %0|%0, %x1}"
2503   [(set_attr "type" "ssecvt")
2504    (set_attr "prefix" "vex")
2505    (set_attr "mode" "V4DF")])
2506
2507 (define_insn "sse2_cvtdq2pd"
2508   [(set (match_operand:V2DF 0 "register_operand" "=x")
2509         (float:V2DF
2510           (vec_select:V2SI
2511             (match_operand:V4SI 1 "nonimmediate_operand" "xm")
2512             (parallel [(const_int 0) (const_int 1)]))))]
2513   "TARGET_SSE2"
2514   "%vcvtdq2pd\t{%1, %0|%0, %q1}"
2515   [(set_attr "type" "ssecvt")
2516    (set_attr "prefix" "maybe_vex")
2517    (set_attr "mode" "V2DF")])
2518
2519 (define_insn "avx_cvtpd2dq256"
2520   [(set (match_operand:V4SI 0 "register_operand" "=x")
2521         (unspec:V4SI [(match_operand:V4DF 1 "nonimmediate_operand" "xm")]
2522                      UNSPEC_FIX_NOTRUNC))]
2523   "TARGET_AVX"
2524   "vcvtpd2dq{y}\t{%1, %0|%0, %1}"
2525   [(set_attr "type" "ssecvt")
2526    (set_attr "prefix" "vex")
2527    (set_attr "mode" "OI")])
2528
2529 (define_expand "avx_cvtpd2dq256_2"
2530   [(set (match_operand:V8SI 0 "register_operand" "")
2531         (vec_concat:V8SI
2532           (unspec:V4SI [(match_operand:V4DF 1 "nonimmediate_operand" "")]
2533                        UNSPEC_FIX_NOTRUNC)
2534           (match_dup 2)))]
2535   "TARGET_AVX"
2536   "operands[2] = CONST0_RTX (V4SImode);")
2537
2538 (define_insn "*avx_cvtpd2dq256_2"
2539   [(set (match_operand:V8SI 0 "register_operand" "=x")
2540         (vec_concat:V8SI
2541           (unspec:V4SI [(match_operand:V4DF 1 "nonimmediate_operand" "xm")]
2542                        UNSPEC_FIX_NOTRUNC)
2543           (match_operand:V4SI 2 "const0_operand" "")))]
2544   "TARGET_AVX"
2545   "vcvtpd2dq{y}\t{%1, %x0|%x0, %1}"
2546   [(set_attr "type" "ssecvt")
2547    (set_attr "prefix" "vex")
2548    (set_attr "mode" "OI")])
2549
2550 (define_expand "sse2_cvtpd2dq"
2551   [(set (match_operand:V4SI 0 "register_operand" "")
2552         (vec_concat:V4SI
2553           (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "")]
2554                        UNSPEC_FIX_NOTRUNC)
2555           (match_dup 2)))]
2556   "TARGET_SSE2"
2557   "operands[2] = CONST0_RTX (V2SImode);")
2558
2559 (define_insn "*sse2_cvtpd2dq"
2560   [(set (match_operand:V4SI 0 "register_operand" "=x")
2561         (vec_concat:V4SI
2562           (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
2563                        UNSPEC_FIX_NOTRUNC)
2564           (match_operand:V2SI 2 "const0_operand" "")))]
2565   "TARGET_SSE2"
2566 {
2567   if (TARGET_AVX)
2568     return "vcvtpd2dq{x}\t{%1, %0|%0, %1}";
2569   else
2570     return "cvtpd2dq\t{%1, %0|%0, %1}";
2571 }
2572   [(set_attr "type" "ssecvt")
2573    (set_attr "prefix_rep" "1")
2574    (set_attr "prefix_data16" "0")
2575    (set_attr "prefix" "maybe_vex")
2576    (set_attr "mode" "TI")
2577    (set_attr "amdfam10_decode" "double")
2578    (set_attr "athlon_decode" "vector")
2579    (set_attr "bdver1_decode" "double")])
2580
2581 (define_insn "fix_truncv4dfv4si2"
2582   [(set (match_operand:V4SI 0 "register_operand" "=x")
2583         (fix:V4SI (match_operand:V4DF 1 "nonimmediate_operand" "xm")))]
2584   "TARGET_AVX"
2585   "vcvttpd2dq{y}\t{%1, %0|%0, %1}"
2586   [(set_attr "type" "ssecvt")
2587    (set_attr "prefix" "vex")
2588    (set_attr "mode" "OI")])
2589
2590 (define_expand "avx_cvttpd2dq256_2"
2591   [(set (match_operand:V8SI 0 "register_operand" "")
2592         (vec_concat:V8SI
2593           (fix:V4SI (match_operand:V4DF 1 "nonimmediate_operand" ""))
2594           (match_dup 2)))]
2595   "TARGET_AVX"
2596   "operands[2] = CONST0_RTX (V4SImode);")
2597
2598 (define_insn "*avx_cvttpd2dq256_2"
2599   [(set (match_operand:V8SI 0 "register_operand" "=x")
2600         (vec_concat:V8SI
2601           (fix:V4SI (match_operand:V4DF 1 "nonimmediate_operand" "xm"))
2602           (match_operand:V4SI 2 "const0_operand" "")))]
2603   "TARGET_AVX"
2604   "vcvttpd2dq{y}\t{%1, %x0|%x0, %1}"
2605   [(set_attr "type" "ssecvt")
2606    (set_attr "prefix" "vex")
2607    (set_attr "mode" "OI")])
2608
2609 (define_expand "sse2_cvttpd2dq"
2610   [(set (match_operand:V4SI 0 "register_operand" "")
2611         (vec_concat:V4SI
2612           (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" ""))
2613           (match_dup 2)))]
2614   "TARGET_SSE2"
2615   "operands[2] = CONST0_RTX (V2SImode);")
2616
2617 (define_insn "*sse2_cvttpd2dq"
2618   [(set (match_operand:V4SI 0 "register_operand" "=x")
2619         (vec_concat:V4SI
2620           (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm"))
2621           (match_operand:V2SI 2 "const0_operand" "")))]
2622   "TARGET_SSE2"
2623 {
2624   if (TARGET_AVX)
2625     return "vcvttpd2dq{x}\t{%1, %0|%0, %1}";
2626   else
2627     return "cvttpd2dq\t{%1, %0|%0, %1}";
2628 }
2629   [(set_attr "type" "ssecvt")
2630    (set_attr "amdfam10_decode" "double")
2631    (set_attr "athlon_decode" "vector")
2632    (set_attr "bdver1_decode" "double")
2633    (set_attr "prefix" "maybe_vex")
2634    (set_attr "mode" "TI")])
2635
2636 (define_insn "sse2_cvtsd2ss"
2637   [(set (match_operand:V4SF 0 "register_operand" "=x,x,x")
2638         (vec_merge:V4SF
2639           (vec_duplicate:V4SF
2640             (float_truncate:V2SF
2641               (match_operand:V2DF 2 "nonimmediate_operand" "x,m,xm")))
2642           (match_operand:V4SF 1 "register_operand" "0,0,x")
2643           (const_int 1)))]
2644   "TARGET_SSE2"
2645   "@
2646    cvtsd2ss\t{%2, %0|%0, %2}
2647    cvtsd2ss\t{%2, %0|%0, %2}
2648    vcvtsd2ss\t{%2, %1, %0|%0, %1, %2}"
2649   [(set_attr "isa" "noavx,noavx,avx")
2650    (set_attr "type" "ssecvt")
2651    (set_attr "athlon_decode" "vector,double,*")
2652    (set_attr "amdfam10_decode" "vector,double,*")
2653    (set_attr "bdver1_decode" "direct,direct,*")
2654    (set_attr "prefix" "orig,orig,vex")
2655    (set_attr "mode" "SF")])
2656
2657 (define_insn "sse2_cvtss2sd"
2658   [(set (match_operand:V2DF 0 "register_operand" "=x,x,x")
2659         (vec_merge:V2DF
2660           (float_extend:V2DF
2661             (vec_select:V2SF
2662               (match_operand:V4SF 2 "nonimmediate_operand" "x,m,xm")
2663               (parallel [(const_int 0) (const_int 1)])))
2664           (match_operand:V2DF 1 "register_operand" "0,0,x")
2665           (const_int 1)))]
2666   "TARGET_SSE2"
2667   "@
2668    cvtss2sd\t{%2, %0|%0, %2}
2669    cvtss2sd\t{%2, %0|%0, %2}
2670    vcvtss2sd\t{%2, %1, %0|%0, %1, %2}"
2671   [(set_attr "isa" "noavx,noavx,avx")
2672    (set_attr "type" "ssecvt")
2673    (set_attr "amdfam10_decode" "vector,double,*")
2674    (set_attr "athlon_decode" "direct,direct,*")
2675    (set_attr "bdver1_decode" "direct,direct,*")
2676    (set_attr "prefix" "orig,orig,vex")
2677    (set_attr "mode" "DF")])
2678
2679 (define_insn "avx_cvtpd2ps256"
2680   [(set (match_operand:V4SF 0 "register_operand" "=x")
2681         (float_truncate:V4SF
2682           (match_operand:V4DF 1 "nonimmediate_operand" "xm")))]
2683   "TARGET_AVX"
2684   "vcvtpd2ps{y}\t{%1, %0|%0, %1}"
2685   [(set_attr "type" "ssecvt")
2686    (set_attr "prefix" "vex")
2687    (set_attr "mode" "V4SF")])
2688
2689 (define_expand "sse2_cvtpd2ps"
2690   [(set (match_operand:V4SF 0 "register_operand" "")
2691         (vec_concat:V4SF
2692           (float_truncate:V2SF
2693             (match_operand:V2DF 1 "nonimmediate_operand" ""))
2694           (match_dup 2)))]
2695   "TARGET_SSE2"
2696   "operands[2] = CONST0_RTX (V2SFmode);")
2697
2698 (define_insn "*sse2_cvtpd2ps"
2699   [(set (match_operand:V4SF 0 "register_operand" "=x")
2700         (vec_concat:V4SF
2701           (float_truncate:V2SF
2702             (match_operand:V2DF 1 "nonimmediate_operand" "xm"))
2703           (match_operand:V2SF 2 "const0_operand" "")))]
2704   "TARGET_SSE2"
2705 {
2706   if (TARGET_AVX)
2707     return "vcvtpd2ps{x}\t{%1, %0|%0, %1}";
2708   else
2709     return "cvtpd2ps\t{%1, %0|%0, %1}";
2710 }
2711   [(set_attr "type" "ssecvt")
2712    (set_attr "amdfam10_decode" "double")
2713    (set_attr "athlon_decode" "vector")
2714    (set_attr "bdver1_decode" "double")
2715    (set_attr "prefix_data16" "1")
2716    (set_attr "prefix" "maybe_vex")
2717    (set_attr "mode" "V4SF")])
2718
2719 (define_insn "avx_cvtps2pd256"
2720   [(set (match_operand:V4DF 0 "register_operand" "=x")
2721         (float_extend:V4DF
2722           (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
2723   "TARGET_AVX"
2724   "vcvtps2pd\t{%1, %0|%0, %1}"
2725   [(set_attr "type" "ssecvt")
2726    (set_attr "prefix" "vex")
2727    (set_attr "mode" "V4DF")])
2728
2729 (define_insn "*avx_cvtps2pd256_2"
2730   [(set (match_operand:V4DF 0 "register_operand" "=x")
2731         (float_extend:V4DF
2732           (vec_select:V4SF
2733             (match_operand:V8SF 1 "nonimmediate_operand" "xm")
2734             (parallel [(const_int 0) (const_int 1)
2735                        (const_int 2) (const_int 3)]))))]
2736   "TARGET_AVX"
2737   "vcvtps2pd\t{%x1, %0|%0, %x1}"
2738   [(set_attr "type" "ssecvt")
2739    (set_attr "prefix" "vex")
2740    (set_attr "mode" "V4DF")])
2741
2742 (define_insn "sse2_cvtps2pd"
2743   [(set (match_operand:V2DF 0 "register_operand" "=x")
2744         (float_extend:V2DF
2745           (vec_select:V2SF
2746             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
2747             (parallel [(const_int 0) (const_int 1)]))))]
2748   "TARGET_SSE2"
2749   "%vcvtps2pd\t{%1, %0|%0, %q1}"
2750   [(set_attr "type" "ssecvt")
2751    (set_attr "amdfam10_decode" "direct")
2752    (set_attr "athlon_decode" "double")
2753    (set_attr "bdver1_decode" "double")
2754    (set_attr "prefix_data16" "0")
2755    (set_attr "prefix" "maybe_vex")
2756    (set_attr "mode" "V2DF")])
2757
2758 (define_expand "vec_unpacks_hi_v4sf"
2759   [(set (match_dup 2)
2760    (vec_select:V4SF
2761      (vec_concat:V8SF
2762        (match_dup 2)
2763        (match_operand:V4SF 1 "nonimmediate_operand" ""))
2764      (parallel [(const_int 6) (const_int 7)
2765                 (const_int 2) (const_int 3)])))
2766   (set (match_operand:V2DF 0 "register_operand" "")
2767    (float_extend:V2DF
2768      (vec_select:V2SF
2769        (match_dup 2)
2770        (parallel [(const_int 0) (const_int 1)]))))]
2771   "TARGET_SSE2"
2772   "operands[2] = gen_reg_rtx (V4SFmode);")
2773
2774 (define_expand "vec_unpacks_hi_v8sf"
2775   [(set (match_dup 2)
2776         (vec_select:V4SF
2777           (match_operand:V8SF 1 "nonimmediate_operand" "")
2778           (parallel [(const_int 4) (const_int 5)
2779                      (const_int 6) (const_int 7)])))
2780    (set (match_operand:V4DF 0 "register_operand" "")
2781         (float_extend:V4DF
2782           (match_dup 2)))]
2783   "TARGET_AVX"
2784   "operands[2] = gen_reg_rtx (V4SFmode);")
2785
2786 (define_expand "vec_unpacks_lo_v4sf"
2787   [(set (match_operand:V2DF 0 "register_operand" "")
2788         (float_extend:V2DF
2789           (vec_select:V2SF
2790             (match_operand:V4SF 1 "nonimmediate_operand" "")
2791             (parallel [(const_int 0) (const_int 1)]))))]
2792   "TARGET_SSE2")
2793
2794 (define_expand "vec_unpacks_lo_v8sf"
2795   [(set (match_operand:V4DF 0 "register_operand" "")
2796         (float_extend:V4DF
2797           (vec_select:V4SF
2798             (match_operand:V8SF 1 "nonimmediate_operand" "")
2799             (parallel [(const_int 0) (const_int 1)
2800                        (const_int 2) (const_int 3)]))))]
2801   "TARGET_AVX")
2802
2803 (define_mode_attr sseunpackfltmode
2804   [(V8HI "V4SF") (V4SI "V2DF") (V16HI "V8SF") (V8SI "V4DF")])
2805
2806 (define_expand "vec_unpacks_float_hi_<mode>"
2807   [(match_operand:<sseunpackfltmode> 0 "register_operand" "")
2808    (match_operand:VI2_AVX2 1 "register_operand" "")]
2809   "TARGET_SSE2"
2810 {
2811   rtx tmp = gen_reg_rtx (<sseunpackmode>mode);
2812
2813   emit_insn (gen_vec_unpacks_hi_<mode> (tmp, operands[1]));
2814   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2815                           gen_rtx_FLOAT (<sseunpackfltmode>mode, tmp)));
2816   DONE;
2817 })
2818
2819 (define_expand "vec_unpacks_float_lo_<mode>"
2820   [(match_operand:<sseunpackfltmode> 0 "register_operand" "")
2821    (match_operand:VI2_AVX2 1 "register_operand" "")]
2822   "TARGET_SSE2"
2823 {
2824   rtx tmp = gen_reg_rtx (<sseunpackmode>mode);
2825
2826   emit_insn (gen_vec_unpacks_lo_<mode> (tmp, operands[1]));
2827   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2828                           gen_rtx_FLOAT (<sseunpackfltmode>mode, tmp)));
2829   DONE;
2830 })
2831
2832 (define_expand "vec_unpacku_float_hi_<mode>"
2833   [(match_operand:<sseunpackfltmode> 0 "register_operand" "")
2834    (match_operand:VI2_AVX2 1 "register_operand" "")]
2835   "TARGET_SSE2"
2836 {
2837   rtx tmp = gen_reg_rtx (<sseunpackmode>mode);
2838
2839   emit_insn (gen_vec_unpacku_hi_<mode> (tmp, operands[1]));
2840   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2841                           gen_rtx_FLOAT (<sseunpackfltmode>mode, tmp)));
2842   DONE;
2843 })
2844
2845 (define_expand "vec_unpacku_float_lo_<mode>"
2846   [(match_operand:<sseunpackfltmode> 0 "register_operand" "")
2847    (match_operand:VI2_AVX2 1 "register_operand" "")]
2848   "TARGET_SSE2"
2849 {
2850   rtx tmp = gen_reg_rtx (<sseunpackmode>mode);
2851
2852   emit_insn (gen_vec_unpacku_lo_<mode> (tmp, operands[1]));
2853   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2854                           gen_rtx_FLOAT (<sseunpackfltmode>mode, tmp)));
2855   DONE;
2856 })
2857
2858 (define_expand "vec_unpacks_float_hi_v4si"
2859   [(set (match_dup 2)
2860         (vec_select:V4SI
2861           (match_operand:V4SI 1 "nonimmediate_operand" "")
2862           (parallel [(const_int 2) (const_int 3)
2863                      (const_int 2) (const_int 3)])))
2864    (set (match_operand:V2DF 0 "register_operand" "")
2865         (float:V2DF
2866           (vec_select:V2SI
2867           (match_dup 2)
2868             (parallel [(const_int 0) (const_int 1)]))))]
2869   "TARGET_SSE2"
2870   "operands[2] = gen_reg_rtx (V4SImode);")
2871
2872 (define_expand "vec_unpacks_float_lo_v4si"
2873   [(set (match_operand:V2DF 0 "register_operand" "")
2874         (float:V2DF
2875           (vec_select:V2SI
2876             (match_operand:V4SI 1 "nonimmediate_operand" "")
2877             (parallel [(const_int 0) (const_int 1)]))))]
2878   "TARGET_SSE2")
2879
2880 (define_expand "vec_unpacks_float_hi_v8si"
2881   [(set (match_dup 2)
2882         (vec_select:V4SI
2883           (match_operand:V8SI 1 "nonimmediate_operand" "")
2884           (parallel [(const_int 4) (const_int 5)
2885                      (const_int 6) (const_int 7)])))
2886    (set (match_operand:V4DF 0 "register_operand" "")
2887         (float:V4DF
2888           (match_dup 2)))]
2889   "TARGET_AVX"
2890   "operands[2] = gen_reg_rtx (V4SImode);")
2891
2892 (define_expand "vec_unpacks_float_lo_v8si"
2893   [(set (match_operand:V4DF 0 "register_operand" "")
2894         (float:V4DF
2895           (vec_select:V4SI
2896             (match_operand:V8SI 1 "nonimmediate_operand" "")
2897             (parallel [(const_int 0) (const_int 1)
2898                        (const_int 2) (const_int 3)]))))]
2899   "TARGET_AVX")
2900
2901 (define_expand "vec_unpacku_float_hi_v4si"
2902   [(set (match_dup 5)
2903         (vec_select:V4SI
2904           (match_operand:V4SI 1 "nonimmediate_operand" "")
2905           (parallel [(const_int 2) (const_int 3)
2906                      (const_int 2) (const_int 3)])))
2907    (set (match_dup 6)
2908         (float:V2DF
2909           (vec_select:V2SI
2910           (match_dup 5)
2911             (parallel [(const_int 0) (const_int 1)]))))
2912    (set (match_dup 7)
2913         (lt:V2DF (match_dup 6) (match_dup 3)))
2914    (set (match_dup 8)
2915         (and:V2DF (match_dup 7) (match_dup 4)))
2916    (set (match_operand:V2DF 0 "register_operand" "")
2917         (plus:V2DF (match_dup 6) (match_dup 8)))]
2918   "TARGET_SSE2"
2919 {
2920   REAL_VALUE_TYPE TWO32r;
2921   rtx x;
2922   int i;
2923
2924   real_ldexp (&TWO32r, &dconst1, 32);
2925   x = const_double_from_real_value (TWO32r, DFmode);
2926
2927   operands[3] = force_reg (V2DFmode, CONST0_RTX (V2DFmode));
2928   operands[4] = force_reg (V2DFmode,
2929                            ix86_build_const_vector (V2DFmode, 1, x));
2930
2931   operands[5] = gen_reg_rtx (V4SImode);
2932
2933   for (i = 6; i < 9; i++)
2934     operands[i] = gen_reg_rtx (V2DFmode);
2935 })
2936
2937 (define_expand "vec_unpacku_float_lo_v4si"
2938   [(set (match_dup 5)
2939         (float:V2DF
2940           (vec_select:V2SI
2941             (match_operand:V4SI 1 "nonimmediate_operand" "")
2942             (parallel [(const_int 0) (const_int 1)]))))
2943    (set (match_dup 6)
2944         (lt:V2DF (match_dup 5) (match_dup 3)))
2945    (set (match_dup 7)
2946         (and:V2DF (match_dup 6) (match_dup 4)))
2947    (set (match_operand:V2DF 0 "register_operand" "")
2948         (plus:V2DF (match_dup 5) (match_dup 7)))]
2949   "TARGET_SSE2"
2950 {
2951   REAL_VALUE_TYPE TWO32r;
2952   rtx x;
2953   int i;
2954
2955   real_ldexp (&TWO32r, &dconst1, 32);
2956   x = const_double_from_real_value (TWO32r, DFmode);
2957
2958   operands[3] = force_reg (V2DFmode, CONST0_RTX (V2DFmode));
2959   operands[4] = force_reg (V2DFmode,
2960                            ix86_build_const_vector (V2DFmode, 1, x));
2961
2962   for (i = 5; i < 8; i++)
2963     operands[i] = gen_reg_rtx (V2DFmode);
2964 })
2965
2966 (define_expand "vec_unpacku_float_hi_v8si"
2967   [(match_operand:V4DF 0 "register_operand" "")
2968    (match_operand:V8SI 1 "register_operand" "")]
2969   "TARGET_AVX"
2970 {
2971   REAL_VALUE_TYPE TWO32r;
2972   rtx x, tmp[6];
2973   int i;
2974
2975   real_ldexp (&TWO32r, &dconst1, 32);
2976   x = const_double_from_real_value (TWO32r, DFmode);
2977
2978   tmp[0] = force_reg (V4DFmode, CONST0_RTX (V4DFmode));
2979   tmp[1] = force_reg (V4DFmode, ix86_build_const_vector (V4DFmode, 1, x));
2980   tmp[5] = gen_reg_rtx (V4SImode);
2981
2982   for (i = 2; i < 5; i++)
2983     tmp[i] = gen_reg_rtx (V4DFmode);
2984   emit_insn (gen_vec_extract_hi_v8si (tmp[5], operands[1]));
2985   emit_insn (gen_floatv4siv4df2 (tmp[2], tmp[5]));
2986   emit_insn (gen_rtx_SET (VOIDmode, tmp[3],
2987                           gen_rtx_LT (V4DFmode, tmp[2], tmp[0])));
2988   emit_insn (gen_andv4df3 (tmp[4], tmp[3], tmp[1]));
2989   emit_insn (gen_addv4df3 (operands[0], tmp[2], tmp[4]));
2990   DONE;
2991 })
2992
2993 (define_expand "vec_unpacku_float_lo_v8si"
2994   [(match_operand:V4DF 0 "register_operand" "")
2995    (match_operand:V8SI 1 "nonimmediate_operand" "")]
2996   "TARGET_AVX"
2997 {
2998   REAL_VALUE_TYPE TWO32r;
2999   rtx x, tmp[5];
3000   int i;
3001
3002   real_ldexp (&TWO32r, &dconst1, 32);
3003   x = const_double_from_real_value (TWO32r, DFmode);
3004
3005   tmp[0] = force_reg (V4DFmode, CONST0_RTX (V4DFmode));
3006   tmp[1] = force_reg (V4DFmode, ix86_build_const_vector (V4DFmode, 1, x));
3007
3008   for (i = 2; i < 5; i++)
3009     tmp[i] = gen_reg_rtx (V4DFmode);
3010   emit_insn (gen_avx_cvtdq2pd256_2 (tmp[2], operands[1]));
3011   emit_insn (gen_rtx_SET (VOIDmode, tmp[3],
3012                           gen_rtx_LT (V4DFmode, tmp[2], tmp[0])));
3013   emit_insn (gen_andv4df3 (tmp[4], tmp[3], tmp[1]));
3014   emit_insn (gen_addv4df3 (operands[0], tmp[2], tmp[4]));
3015   DONE;
3016 })
3017
3018 (define_expand "vec_pack_trunc_v4df"
3019   [(set (match_dup 3)
3020         (float_truncate:V4SF
3021           (match_operand:V4DF 1 "nonimmediate_operand" "")))
3022    (set (match_dup 4)
3023         (float_truncate:V4SF
3024           (match_operand:V4DF 2 "nonimmediate_operand" "")))
3025    (set (match_operand:V8SF 0 "register_operand" "")
3026         (vec_concat:V8SF
3027           (match_dup 3)
3028           (match_dup 4)))]
3029   "TARGET_AVX"
3030 {
3031   operands[3] = gen_reg_rtx (V4SFmode);
3032   operands[4] = gen_reg_rtx (V4SFmode);
3033 })
3034
3035 (define_expand "vec_pack_trunc_v2df"
3036   [(match_operand:V4SF 0 "register_operand" "")
3037    (match_operand:V2DF 1 "nonimmediate_operand" "")
3038    (match_operand:V2DF 2 "nonimmediate_operand" "")]
3039   "TARGET_SSE2"
3040 {
3041   rtx r1, r2;
3042
3043   r1 = gen_reg_rtx (V4SFmode);
3044   r2 = gen_reg_rtx (V4SFmode);
3045
3046   emit_insn (gen_sse2_cvtpd2ps (r1, operands[1]));
3047   emit_insn (gen_sse2_cvtpd2ps (r2, operands[2]));
3048   emit_insn (gen_sse_movlhps (operands[0], r1, r2));
3049   DONE;
3050 })
3051
3052 (define_expand "vec_pack_sfix_trunc_v4df"
3053   [(match_operand:V8SI 0 "register_operand" "")
3054    (match_operand:V4DF 1 "nonimmediate_operand" "")
3055    (match_operand:V4DF 2 "nonimmediate_operand" "")]
3056   "TARGET_AVX"
3057 {
3058   rtx r1, r2;
3059
3060   r1 = gen_reg_rtx (V8SImode);
3061   r2 = gen_reg_rtx (V8SImode);
3062
3063   emit_insn (gen_avx_cvttpd2dq256_2 (r1, operands[1]));
3064   emit_insn (gen_avx_cvttpd2dq256_2 (r2, operands[2]));
3065   emit_insn (gen_avx_vperm2f128v8si3 (operands[0], r1, r2, GEN_INT (0x20)));
3066   DONE;
3067 })
3068
3069 (define_expand "vec_pack_sfix_trunc_v2df"
3070   [(match_operand:V4SI 0 "register_operand" "")
3071    (match_operand:V2DF 1 "nonimmediate_operand" "")
3072    (match_operand:V2DF 2 "nonimmediate_operand" "")]
3073   "TARGET_SSE2"
3074 {
3075   rtx r1, r2;
3076
3077   r1 = gen_reg_rtx (V4SImode);
3078   r2 = gen_reg_rtx (V4SImode);
3079
3080   emit_insn (gen_sse2_cvttpd2dq (r1, operands[1]));
3081   emit_insn (gen_sse2_cvttpd2dq (r2, operands[2]));
3082   emit_insn (gen_vec_interleave_lowv2di (gen_lowpart (V2DImode, operands[0]),
3083                                          gen_lowpart (V2DImode, r1),
3084                                          gen_lowpart (V2DImode, r2)));
3085   DONE;
3086 })
3087
3088 (define_mode_attr ssepackfltmode
3089   [(V4DF "V8SI") (V2DF "V4SI")])
3090
3091 (define_expand "vec_pack_ufix_trunc_<mode>"
3092   [(match_operand:<ssepackfltmode> 0 "register_operand" "")
3093    (match_operand:VF2 1 "register_operand" "")
3094    (match_operand:VF2 2 "register_operand" "")]
3095   "TARGET_SSE2"
3096 {
3097   rtx tmp[7];
3098   tmp[0] = ix86_expand_adjust_ufix_to_sfix_si (operands[1], &tmp[2]);
3099   tmp[1] = ix86_expand_adjust_ufix_to_sfix_si (operands[2], &tmp[3]);
3100   tmp[4] = gen_reg_rtx (<ssepackfltmode>mode);
3101   emit_insn (gen_vec_pack_sfix_trunc_<mode> (tmp[4], tmp[0], tmp[1]));
3102   if (<ssepackfltmode>mode == V4SImode || TARGET_AVX2)
3103     {
3104       tmp[5] = gen_reg_rtx (<ssepackfltmode>mode);
3105       ix86_expand_vec_extract_even_odd (tmp[5], tmp[2], tmp[3], 0);
3106     }
3107   else
3108     {
3109       tmp[5] = gen_reg_rtx (V8SFmode);
3110       ix86_expand_vec_extract_even_odd (tmp[5], gen_lowpart (V8SFmode, tmp[2]),
3111                                         gen_lowpart (V8SFmode, tmp[3]), 0);
3112       tmp[5] = gen_lowpart (V8SImode, tmp[5]);
3113     }
3114   tmp[6] = expand_simple_binop (<ssepackfltmode>mode, XOR, tmp[4], tmp[5],
3115                                 operands[0], 0, OPTAB_DIRECT);
3116   if (tmp[6] != operands[0])
3117     emit_move_insn (operands[0], tmp[6]);
3118   DONE;
3119 })
3120
3121 (define_expand "vec_pack_sfix_v4df"
3122   [(match_operand:V8SI 0 "register_operand" "")
3123    (match_operand:V4DF 1 "nonimmediate_operand" "")
3124    (match_operand:V4DF 2 "nonimmediate_operand" "")]
3125   "TARGET_AVX"
3126 {
3127   rtx r1, r2;
3128
3129   r1 = gen_reg_rtx (V8SImode);
3130   r2 = gen_reg_rtx (V8SImode);
3131
3132   emit_insn (gen_avx_cvtpd2dq256_2 (r1, operands[1]));
3133   emit_insn (gen_avx_cvtpd2dq256_2 (r2, operands[2]));
3134   emit_insn (gen_avx_vperm2f128v8si3 (operands[0], r1, r2, GEN_INT (0x20)));
3135   DONE;
3136 })
3137
3138 (define_expand "vec_pack_sfix_v2df"
3139   [(match_operand:V4SI 0 "register_operand" "")
3140    (match_operand:V2DF 1 "nonimmediate_operand" "")
3141    (match_operand:V2DF 2 "nonimmediate_operand" "")]
3142   "TARGET_SSE2"
3143 {
3144   rtx r1, r2;
3145
3146   r1 = gen_reg_rtx (V4SImode);
3147   r2 = gen_reg_rtx (V4SImode);
3148
3149   emit_insn (gen_sse2_cvtpd2dq (r1, operands[1]));
3150   emit_insn (gen_sse2_cvtpd2dq (r2, operands[2]));
3151   emit_insn (gen_vec_interleave_lowv2di (gen_lowpart (V2DImode, operands[0]),
3152                                          gen_lowpart (V2DImode, r1),
3153                                          gen_lowpart (V2DImode, r2)));
3154   DONE;
3155 })
3156
3157 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3158 ;;
3159 ;; Parallel single-precision floating point element swizzling
3160 ;;
3161 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3162
3163 (define_expand "sse_movhlps_exp"
3164   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3165         (vec_select:V4SF
3166           (vec_concat:V8SF
3167             (match_operand:V4SF 1 "nonimmediate_operand" "")
3168             (match_operand:V4SF 2 "nonimmediate_operand" ""))
3169           (parallel [(const_int 6)
3170                      (const_int 7)
3171                      (const_int 2)
3172                      (const_int 3)])))]
3173   "TARGET_SSE"
3174 {
3175   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);
3176
3177   emit_insn (gen_sse_movhlps (dst, operands[1], operands[2]));
3178
3179   /* Fix up the destination if needed.  */
3180   if (dst != operands[0])
3181     emit_move_insn (operands[0], dst);
3182
3183   DONE;
3184 })
3185
3186 (define_insn "sse_movhlps"
3187   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,x,x,m")
3188         (vec_select:V4SF
3189           (vec_concat:V8SF
3190             (match_operand:V4SF 1 "nonimmediate_operand" " 0,x,0,x,0")
3191             (match_operand:V4SF 2 "nonimmediate_operand" " x,x,o,o,x"))
3192           (parallel [(const_int 6)
3193                      (const_int 7)
3194                      (const_int 2)
3195                      (const_int 3)])))]
3196   "TARGET_SSE && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
3197   "@
3198    movhlps\t{%2, %0|%0, %2}
3199    vmovhlps\t{%2, %1, %0|%0, %1, %2}
3200    movlps\t{%H2, %0|%0, %H2}
3201    vmovlps\t{%H2, %1, %0|%0, %1, %H2}
3202    %vmovhps\t{%2, %0|%0, %2}"
3203   [(set_attr "isa" "noavx,avx,noavx,avx,*")
3204    (set_attr "type" "ssemov")
3205    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex")
3206    (set_attr "mode" "V4SF,V4SF,V2SF,V2SF,V2SF")])
3207
3208 (define_expand "sse_movlhps_exp"
3209   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3210         (vec_select:V4SF
3211           (vec_concat:V8SF
3212             (match_operand:V4SF 1 "nonimmediate_operand" "")
3213             (match_operand:V4SF 2 "nonimmediate_operand" ""))
3214           (parallel [(const_int 0)
3215                      (const_int 1)
3216                      (const_int 4)
3217                      (const_int 5)])))]
3218   "TARGET_SSE"
3219 {
3220   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);
3221
3222   emit_insn (gen_sse_movlhps (dst, operands[1], operands[2]));
3223
3224   /* Fix up the destination if needed.  */
3225   if (dst != operands[0])
3226     emit_move_insn (operands[0], dst);
3227
3228   DONE;
3229 })
3230
3231 (define_insn "sse_movlhps"
3232   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,x,x,o")
3233         (vec_select:V4SF
3234           (vec_concat:V8SF
3235             (match_operand:V4SF 1 "nonimmediate_operand" " 0,x,0,x,0")
3236             (match_operand:V4SF 2 "nonimmediate_operand" " x,x,m,x,x"))
3237           (parallel [(const_int 0)
3238                      (const_int 1)
3239                      (const_int 4)
3240                      (const_int 5)])))]
3241   "TARGET_SSE && ix86_binary_operator_ok (UNKNOWN, V4SFmode, operands)"
3242   "@
3243    movlhps\t{%2, %0|%0, %2}
3244    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3245    movhps\t{%2, %0|%0, %2}
3246    vmovhps\t{%2, %1, %0|%0, %1, %2}
3247    %vmovlps\t{%2, %H0|%H0, %2}"
3248   [(set_attr "isa" "noavx,avx,noavx,avx,*")
3249    (set_attr "type" "ssemov")
3250    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex")
3251    (set_attr "mode" "V4SF,V4SF,V2SF,V2SF,V2SF")])
3252
3253 ;; Recall that the 256-bit unpck insns only shuffle within their lanes.
3254 (define_insn "avx_unpckhps256"
3255   [(set (match_operand:V8SF 0 "register_operand" "=x")
3256         (vec_select:V8SF
3257           (vec_concat:V16SF
3258             (match_operand:V8SF 1 "register_operand" "x")
3259             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3260           (parallel [(const_int 2) (const_int 10)
3261                      (const_int 3) (const_int 11)
3262                      (const_int 6) (const_int 14)
3263                      (const_int 7) (const_int 15)])))]
3264   "TARGET_AVX"
3265   "vunpckhps\t{%2, %1, %0|%0, %1, %2}"
3266   [(set_attr "type" "sselog")
3267    (set_attr "prefix" "vex")
3268    (set_attr "mode" "V8SF")])
3269
3270 (define_expand "vec_interleave_highv8sf"
3271   [(set (match_dup 3)
3272         (vec_select:V8SF
3273           (vec_concat:V16SF
3274             (match_operand:V8SF 1 "register_operand" "x")
3275             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3276           (parallel [(const_int 0) (const_int 8)
3277                      (const_int 1) (const_int 9)
3278                      (const_int 4) (const_int 12)
3279                      (const_int 5) (const_int 13)])))
3280    (set (match_dup 4)
3281         (vec_select:V8SF
3282           (vec_concat:V16SF
3283             (match_dup 1)
3284             (match_dup 2))
3285           (parallel [(const_int 2) (const_int 10)
3286                      (const_int 3) (const_int 11)
3287                      (const_int 6) (const_int 14)
3288                      (const_int 7) (const_int 15)])))
3289    (set (match_operand:V8SF 0 "register_operand" "")
3290         (vec_select:V8SF
3291           (vec_concat:V16SF
3292             (match_dup 3)
3293             (match_dup 4))
3294           (parallel [(const_int 4) (const_int 5)
3295                      (const_int 6) (const_int 7)
3296                      (const_int 12) (const_int 13)
3297                      (const_int 14) (const_int 15)])))]
3298  "TARGET_AVX"
3299 {
3300   operands[3] = gen_reg_rtx (V8SFmode);
3301   operands[4] = gen_reg_rtx (V8SFmode);
3302 })
3303
3304 (define_insn "vec_interleave_highv4sf"
3305   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
3306         (vec_select:V4SF
3307           (vec_concat:V8SF
3308             (match_operand:V4SF 1 "register_operand" "0,x")
3309             (match_operand:V4SF 2 "nonimmediate_operand" "xm,xm"))
3310           (parallel [(const_int 2) (const_int 6)
3311                      (const_int 3) (const_int 7)])))]
3312   "TARGET_SSE"
3313   "@
3314    unpckhps\t{%2, %0|%0, %2}
3315    vunpckhps\t{%2, %1, %0|%0, %1, %2}"
3316   [(set_attr "isa" "noavx,avx")
3317    (set_attr "type" "sselog")
3318    (set_attr "prefix" "orig,vex")
3319    (set_attr "mode" "V4SF")])
3320
3321 ;; Recall that the 256-bit unpck insns only shuffle within their lanes.
3322 (define_insn "avx_unpcklps256"
3323   [(set (match_operand:V8SF 0 "register_operand" "=x")
3324         (vec_select:V8SF
3325           (vec_concat:V16SF
3326             (match_operand:V8SF 1 "register_operand" "x")
3327             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3328           (parallel [(const_int 0) (const_int 8)
3329                      (const_int 1) (const_int 9)
3330                      (const_int 4) (const_int 12)
3331                      (const_int 5) (const_int 13)])))]
3332   "TARGET_AVX"
3333   "vunpcklps\t{%2, %1, %0|%0, %1, %2}"
3334   [(set_attr "type" "sselog")
3335    (set_attr "prefix" "vex")
3336    (set_attr "mode" "V8SF")])
3337
3338 (define_expand "vec_interleave_lowv8sf"
3339   [(set (match_dup 3)
3340         (vec_select:V8SF
3341           (vec_concat:V16SF
3342             (match_operand:V8SF 1 "register_operand" "x")
3343             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3344           (parallel [(const_int 0) (const_int 8)
3345                      (const_int 1) (const_int 9)
3346                      (const_int 4) (const_int 12)
3347                      (const_int 5) (const_int 13)])))
3348    (set (match_dup 4)
3349         (vec_select:V8SF
3350           (vec_concat:V16SF
3351             (match_dup 1)
3352             (match_dup 2))
3353           (parallel [(const_int 2) (const_int 10)
3354                      (const_int 3) (const_int 11)
3355                      (const_int 6) (const_int 14)
3356                      (const_int 7) (const_int 15)])))
3357    (set (match_operand:V8SF 0 "register_operand" "")
3358         (vec_select:V8SF
3359           (vec_concat:V16SF
3360             (match_dup 3)
3361             (match_dup 4))
3362           (parallel [(const_int 0) (const_int 1)
3363                      (const_int 2) (const_int 3)
3364                      (const_int 8) (const_int 9)
3365                      (const_int 10) (const_int 11)])))]
3366  "TARGET_AVX"
3367 {
3368   operands[3] = gen_reg_rtx (V8SFmode);
3369   operands[4] = gen_reg_rtx (V8SFmode);
3370 })
3371
3372 (define_insn "vec_interleave_lowv4sf"
3373   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
3374         (vec_select:V4SF
3375           (vec_concat:V8SF
3376             (match_operand:V4SF 1 "register_operand" "0,x")
3377             (match_operand:V4SF 2 "nonimmediate_operand" "xm,xm"))
3378           (parallel [(const_int 0) (const_int 4)
3379                      (const_int 1) (const_int 5)])))]
3380   "TARGET_SSE"
3381   "@
3382    unpcklps\t{%2, %0|%0, %2}
3383    vunpcklps\t{%2, %1, %0|%0, %1, %2}"
3384   [(set_attr "isa" "noavx,avx")
3385    (set_attr "type" "sselog")
3386    (set_attr "prefix" "orig,vex")
3387    (set_attr "mode" "V4SF")])
3388
3389 ;; These are modeled with the same vec_concat as the others so that we
3390 ;; capture users of shufps that can use the new instructions
3391 (define_insn "avx_movshdup256"
3392   [(set (match_operand:V8SF 0 "register_operand" "=x")
3393         (vec_select:V8SF
3394           (vec_concat:V16SF
3395             (match_operand:V8SF 1 "nonimmediate_operand" "xm")
3396             (match_dup 1))
3397           (parallel [(const_int 1) (const_int 1)
3398                      (const_int 3) (const_int 3)
3399                      (const_int 5) (const_int 5)
3400                      (const_int 7) (const_int 7)])))]
3401   "TARGET_AVX"
3402   "vmovshdup\t{%1, %0|%0, %1}"
3403   [(set_attr "type" "sse")
3404    (set_attr "prefix" "vex")
3405    (set_attr "mode" "V8SF")])
3406
3407 (define_insn "sse3_movshdup"
3408   [(set (match_operand:V4SF 0 "register_operand" "=x")
3409         (vec_select:V4SF
3410           (vec_concat:V8SF
3411             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
3412             (match_dup 1))
3413           (parallel [(const_int 1)
3414                      (const_int 1)
3415                      (const_int 7)
3416                      (const_int 7)])))]
3417   "TARGET_SSE3"
3418   "%vmovshdup\t{%1, %0|%0, %1}"
3419   [(set_attr "type" "sse")
3420    (set_attr "prefix_rep" "1")
3421    (set_attr "prefix" "maybe_vex")
3422    (set_attr "mode" "V4SF")])
3423
3424 (define_insn "avx_movsldup256"
3425   [(set (match_operand:V8SF 0 "register_operand" "=x")
3426         (vec_select:V8SF
3427           (vec_concat:V16SF
3428             (match_operand:V8SF 1 "nonimmediate_operand" "xm")
3429             (match_dup 1))
3430           (parallel [(const_int 0) (const_int 0)
3431                      (const_int 2) (const_int 2)
3432                      (const_int 4) (const_int 4)
3433                      (const_int 6) (const_int 6)])))]
3434   "TARGET_AVX"
3435   "vmovsldup\t{%1, %0|%0, %1}"
3436   [(set_attr "type" "sse")
3437    (set_attr "prefix" "vex")
3438    (set_attr "mode" "V8SF")])
3439
3440 (define_insn "sse3_movsldup"
3441   [(set (match_operand:V4SF 0 "register_operand" "=x")
3442         (vec_select:V4SF
3443           (vec_concat:V8SF
3444             (match_operand:V4SF 1 "nonimmediate_operand" "xm")
3445             (match_dup 1))
3446           (parallel [(const_int 0)
3447                      (const_int 0)
3448                      (const_int 6)
3449                      (const_int 6)])))]
3450   "TARGET_SSE3"
3451   "%vmovsldup\t{%1, %0|%0, %1}"
3452   [(set_attr "type" "sse")
3453    (set_attr "prefix_rep" "1")
3454    (set_attr "prefix" "maybe_vex")
3455    (set_attr "mode" "V4SF")])
3456
3457 (define_expand "avx_shufps256"
3458   [(match_operand:V8SF 0 "register_operand" "")
3459    (match_operand:V8SF 1 "register_operand" "")
3460    (match_operand:V8SF 2 "nonimmediate_operand" "")
3461    (match_operand:SI 3 "const_int_operand" "")]
3462   "TARGET_AVX"
3463 {
3464   int mask = INTVAL (operands[3]);
3465   emit_insn (gen_avx_shufps256_1 (operands[0], operands[1], operands[2],
3466                                   GEN_INT ((mask >> 0) & 3),
3467                                   GEN_INT ((mask >> 2) & 3),
3468                                   GEN_INT (((mask >> 4) & 3) + 8),
3469                                   GEN_INT (((mask >> 6) & 3) + 8),
3470                                   GEN_INT (((mask >> 0) & 3) + 4),
3471                                   GEN_INT (((mask >> 2) & 3) + 4),
3472                                   GEN_INT (((mask >> 4) & 3) + 12),
3473                                   GEN_INT (((mask >> 6) & 3) + 12)));
3474   DONE;
3475 })
3476
3477 ;; One bit in mask selects 2 elements.
3478 (define_insn "avx_shufps256_1"
3479   [(set (match_operand:V8SF 0 "register_operand" "=x")
3480         (vec_select:V8SF
3481           (vec_concat:V16SF
3482             (match_operand:V8SF 1 "register_operand" "x")
3483             (match_operand:V8SF 2 "nonimmediate_operand" "xm"))
3484           (parallel [(match_operand 3  "const_0_to_3_operand"   "")
3485                      (match_operand 4  "const_0_to_3_operand"   "")
3486                      (match_operand 5  "const_8_to_11_operand"  "")
3487                      (match_operand 6  "const_8_to_11_operand"  "")
3488                      (match_operand 7  "const_4_to_7_operand"   "")
3489                      (match_operand 8  "const_4_to_7_operand"   "")
3490                      (match_operand 9  "const_12_to_15_operand" "")
3491                      (match_operand 10 "const_12_to_15_operand" "")])))]
3492   "TARGET_AVX
3493    && (INTVAL (operands[3]) == (INTVAL (operands[7]) - 4)
3494        && INTVAL (operands[4]) == (INTVAL (operands[8]) - 4)
3495        && INTVAL (operands[5]) == (INTVAL (operands[9]) - 4)
3496        && INTVAL (operands[6]) == (INTVAL (operands[10]) - 4))"
3497 {
3498   int mask;
3499   mask = INTVAL (operands[3]);
3500   mask |= INTVAL (operands[4]) << 2;
3501   mask |= (INTVAL (operands[5]) - 8) << 4;
3502   mask |= (INTVAL (operands[6]) - 8) << 6;
3503   operands[3] = GEN_INT (mask);
3504
3505   return "vshufps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3506 }
3507   [(set_attr "type" "sselog")
3508    (set_attr "length_immediate" "1")
3509    (set_attr "prefix" "vex")
3510    (set_attr "mode" "V8SF")])
3511
3512 (define_expand "sse_shufps"
3513   [(match_operand:V4SF 0 "register_operand" "")
3514    (match_operand:V4SF 1 "register_operand" "")
3515    (match_operand:V4SF 2 "nonimmediate_operand" "")
3516    (match_operand:SI 3 "const_int_operand" "")]
3517   "TARGET_SSE"
3518 {
3519   int mask = INTVAL (operands[3]);
3520   emit_insn (gen_sse_shufps_v4sf (operands[0], operands[1], operands[2],
3521                                GEN_INT ((mask >> 0) & 3),
3522                                GEN_INT ((mask >> 2) & 3),
3523                                GEN_INT (((mask >> 4) & 3) + 4),
3524                                GEN_INT (((mask >> 6) & 3) + 4)));
3525   DONE;
3526 })
3527
3528 (define_insn "sse_shufps_<mode>"
3529   [(set (match_operand:VI4F_128 0 "register_operand" "=x,x")
3530         (vec_select:VI4F_128
3531           (vec_concat:<ssedoublevecmode>
3532             (match_operand:VI4F_128 1 "register_operand" "0,x")
3533             (match_operand:VI4F_128 2 "nonimmediate_operand" "xm,xm"))
3534           (parallel [(match_operand 3 "const_0_to_3_operand" "")
3535                      (match_operand 4 "const_0_to_3_operand" "")
3536                      (match_operand 5 "const_4_to_7_operand" "")
3537                      (match_operand 6 "const_4_to_7_operand" "")])))]
3538   "TARGET_SSE"
3539 {
3540   int mask = 0;
3541   mask |= INTVAL (operands[3]) << 0;
3542   mask |= INTVAL (operands[4]) << 2;
3543   mask |= (INTVAL (operands[5]) - 4) << 4;
3544   mask |= (INTVAL (operands[6]) - 4) << 6;
3545   operands[3] = GEN_INT (mask);
3546
3547   switch (which_alternative)
3548     {
3549     case 0:
3550       return "shufps\t{%3, %2, %0|%0, %2, %3}";
3551     case 1:
3552       return "vshufps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3553     default:
3554       gcc_unreachable ();
3555     }
3556 }
3557   [(set_attr "isa" "noavx,avx")
3558    (set_attr "type" "sselog")
3559    (set_attr "length_immediate" "1")
3560    (set_attr "prefix" "orig,vex")
3561    (set_attr "mode" "V4SF")])
3562
3563 (define_insn "sse_storehps"
3564   [(set (match_operand:V2SF 0 "nonimmediate_operand" "=m,x,x")
3565         (vec_select:V2SF
3566           (match_operand:V4SF 1 "nonimmediate_operand" "x,x,o")
3567           (parallel [(const_int 2) (const_int 3)])))]
3568   "TARGET_SSE"
3569   "@
3570    %vmovhps\t{%1, %0|%0, %1}
3571    %vmovhlps\t{%1, %d0|%d0, %1}
3572    %vmovlps\t{%H1, %d0|%d0, %H1}"
3573   [(set_attr "type" "ssemov")
3574    (set_attr "prefix" "maybe_vex")
3575    (set_attr "mode" "V2SF,V4SF,V2SF")])
3576
3577 (define_expand "sse_loadhps_exp"
3578   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3579         (vec_concat:V4SF
3580           (vec_select:V2SF
3581             (match_operand:V4SF 1 "nonimmediate_operand" "")
3582             (parallel [(const_int 0) (const_int 1)]))
3583           (match_operand:V2SF 2 "nonimmediate_operand" "")))]
3584   "TARGET_SSE"
3585 {
3586   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);
3587
3588   emit_insn (gen_sse_loadhps (dst, operands[1], operands[2]));
3589
3590   /* Fix up the destination if needed.  */
3591   if (dst != operands[0])
3592     emit_move_insn (operands[0], dst);
3593
3594   DONE;
3595 })
3596
3597 (define_insn "sse_loadhps"
3598   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,x,x,o")
3599         (vec_concat:V4SF
3600           (vec_select:V2SF
3601             (match_operand:V4SF 1 "nonimmediate_operand" " 0,x,0,x,0")
3602             (parallel [(const_int 0) (const_int 1)]))
3603           (match_operand:V2SF 2 "nonimmediate_operand"   " m,m,x,x,x")))]
3604   "TARGET_SSE"
3605   "@
3606    movhps\t{%2, %0|%0, %2}
3607    vmovhps\t{%2, %1, %0|%0, %1, %2}
3608    movlhps\t{%2, %0|%0, %2}
3609    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3610    %vmovlps\t{%2, %H0|%H0, %2}"
3611   [(set_attr "isa" "noavx,avx,noavx,avx,*")
3612    (set_attr "type" "ssemov")
3613    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex")
3614    (set_attr "mode" "V2SF,V2SF,V4SF,V4SF,V2SF")])
3615
3616 (define_insn "sse_storelps"
3617   [(set (match_operand:V2SF 0 "nonimmediate_operand"   "=m,x,x")
3618         (vec_select:V2SF
3619           (match_operand:V4SF 1 "nonimmediate_operand" " x,x,m")
3620           (parallel [(const_int 0) (const_int 1)])))]
3621   "TARGET_SSE"
3622   "@
3623    %vmovlps\t{%1, %0|%0, %1}
3624    %vmovaps\t{%1, %0|%0, %1}
3625    %vmovlps\t{%1, %d0|%d0, %1}"
3626   [(set_attr "type" "ssemov")
3627    (set_attr "prefix" "maybe_vex")
3628    (set_attr "mode" "V2SF,V4SF,V2SF")])
3629
3630 (define_expand "sse_loadlps_exp"
3631   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
3632         (vec_concat:V4SF
3633           (match_operand:V2SF 2 "nonimmediate_operand" "")
3634           (vec_select:V2SF
3635             (match_operand:V4SF 1 "nonimmediate_operand" "")
3636             (parallel [(const_int 2) (const_int 3)]))))]
3637   "TARGET_SSE"
3638 {
3639   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V4SFmode, operands);
3640
3641   emit_insn (gen_sse_loadlps (dst, operands[1], operands[2]));
3642
3643   /* Fix up the destination if needed.  */
3644   if (dst != operands[0])
3645     emit_move_insn (operands[0], dst);
3646
3647   DONE;
3648 })
3649
3650 (define_insn "sse_loadlps"
3651   [(set (match_operand:V4SF 0 "nonimmediate_operand"     "=x,x,x,x,m")
3652         (vec_concat:V4SF
3653           (match_operand:V2SF 2 "nonimmediate_operand"   " 0,x,m,x,x")
3654           (vec_select:V2SF
3655             (match_operand:V4SF 1 "nonimmediate_operand" " x,x,0,x,0")
3656             (parallel [(const_int 2) (const_int 3)]))))]
3657   "TARGET_SSE"
3658   "@
3659    shufps\t{$0xe4, %1, %0|%0, %1, 0xe4}
3660    vshufps\t{$0xe4, %1, %2, %0|%0, %2, %1, 0xe4}
3661    movlps\t{%2, %0|%0, %2}
3662    vmovlps\t{%2, %1, %0|%0, %1, %2}
3663    %vmovlps\t{%2, %0|%0, %2}"
3664   [(set_attr "isa" "noavx,avx,noavx,avx,*")
3665    (set_attr "type" "sselog,sselog,ssemov,ssemov,ssemov")
3666    (set_attr "length_immediate" "1,1,*,*,*")
3667    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex")
3668    (set_attr "mode" "V4SF,V4SF,V2SF,V2SF,V2SF")])
3669
3670 (define_insn "sse_movss"
3671   [(set (match_operand:V4SF 0 "register_operand"   "=x,x")
3672         (vec_merge:V4SF
3673           (match_operand:V4SF 2 "register_operand" " x,x")
3674           (match_operand:V4SF 1 "register_operand" " 0,x")
3675           (const_int 1)))]
3676   "TARGET_SSE"
3677   "@
3678    movss\t{%2, %0|%0, %2}
3679    vmovss\t{%2, %1, %0|%0, %1, %2}"
3680   [(set_attr "isa" "noavx,avx")
3681    (set_attr "type" "ssemov")
3682    (set_attr "prefix" "orig,vex")
3683    (set_attr "mode" "SF")])
3684
3685 (define_insn "avx2_vec_dup<mode>"
3686   [(set (match_operand:VF1 0 "register_operand" "=x")
3687         (vec_duplicate:VF1
3688           (vec_select:SF
3689             (match_operand:V4SF 1 "register_operand" "x")
3690             (parallel [(const_int 0)]))))]
3691   "TARGET_AVX2"
3692   "vbroadcastss\t{%1, %0|%0, %1}"
3693   [(set_attr "type" "sselog1")
3694     (set_attr "prefix" "vex")
3695     (set_attr "mode" "<MODE>")])
3696
3697 (define_insn "vec_dupv4sf"
3698   [(set (match_operand:V4SF 0 "register_operand" "=x,x,x")
3699         (vec_duplicate:V4SF
3700           (match_operand:SF 1 "nonimmediate_operand" "x,m,0")))]
3701   "TARGET_SSE"
3702   "@
3703    vshufps\t{$0, %1, %1, %0|%0, %1, %1, 0}
3704    vbroadcastss\t{%1, %0|%0, %1}
3705    shufps\t{$0, %0, %0|%0, %0, 0}"
3706   [(set_attr "isa" "avx,avx,noavx")
3707    (set_attr "type" "sselog1,ssemov,sselog1")
3708    (set_attr "length_immediate" "1,0,1")
3709    (set_attr "prefix_extra" "0,1,*")
3710    (set_attr "prefix" "vex,vex,orig")
3711    (set_attr "mode" "V4SF")])
3712
3713 ;; Although insertps takes register source, we prefer
3714 ;; unpcklps with register source since it is shorter.
3715 (define_insn "*vec_concatv2sf_sse4_1"
3716   [(set (match_operand:V2SF 0 "register_operand"     "=x,x,x,x,x,*y ,*y")
3717         (vec_concat:V2SF
3718           (match_operand:SF 1 "nonimmediate_operand" " 0,x,0,x,m, 0 , m")
3719           (match_operand:SF 2 "vector_move_operand"  " x,x,m,m,C,*ym, C")))]
3720   "TARGET_SSE4_1"
3721   "@
3722    unpcklps\t{%2, %0|%0, %2}
3723    vunpcklps\t{%2, %1, %0|%0, %1, %2}
3724    insertps\t{$0x10, %2, %0|%0, %2, 0x10}
3725    vinsertps\t{$0x10, %2, %1, %0|%0, %1, %2, 0x10}
3726    %vmovss\t{%1, %0|%0, %1}
3727    punpckldq\t{%2, %0|%0, %2}
3728    movd\t{%1, %0|%0, %1}"
3729   [(set_attr "isa" "noavx,avx,noavx,avx,*,*,*")
3730    (set_attr "type" "sselog,sselog,sselog,sselog,ssemov,mmxcvt,mmxmov")
3731    (set_attr "prefix_data16" "*,*,1,*,*,*,*")
3732    (set_attr "prefix_extra" "*,*,1,1,*,*,*")
3733    (set_attr "length_immediate" "*,*,1,1,*,*,*")
3734    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex,orig,orig")
3735    (set_attr "mode" "V4SF,V4SF,V4SF,V4SF,SF,DI,DI")])
3736
3737 ;; ??? In theory we can match memory for the MMX alternative, but allowing
3738 ;; nonimmediate_operand for operand 2 and *not* allowing memory for the SSE
3739 ;; alternatives pretty much forces the MMX alternative to be chosen.
3740 (define_insn "*vec_concatv2sf_sse"
3741   [(set (match_operand:V2SF 0 "register_operand"     "=x,x,*y,*y")
3742         (vec_concat:V2SF
3743           (match_operand:SF 1 "nonimmediate_operand" " 0,m, 0, m")
3744           (match_operand:SF 2 "reg_or_0_operand"     " x,C,*y, C")))]
3745   "TARGET_SSE"
3746   "@
3747    unpcklps\t{%2, %0|%0, %2}
3748    movss\t{%1, %0|%0, %1}
3749    punpckldq\t{%2, %0|%0, %2}
3750    movd\t{%1, %0|%0, %1}"
3751   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
3752    (set_attr "mode" "V4SF,SF,DI,DI")])
3753
3754 (define_insn "*vec_concatv4sf"
3755   [(set (match_operand:V4SF 0 "register_operand"       "=x,x,x,x")
3756         (vec_concat:V4SF
3757           (match_operand:V2SF 1 "register_operand"     " 0,x,0,x")
3758           (match_operand:V2SF 2 "nonimmediate_operand" " x,x,m,m")))]
3759   "TARGET_SSE"
3760   "@
3761    movlhps\t{%2, %0|%0, %2}
3762    vmovlhps\t{%2, %1, %0|%0, %1, %2}
3763    movhps\t{%2, %0|%0, %2}
3764    vmovhps\t{%2, %1, %0|%0, %1, %2}"
3765   [(set_attr "isa" "noavx,avx,noavx,avx")
3766    (set_attr "type" "ssemov")
3767    (set_attr "prefix" "orig,vex,orig,vex")
3768    (set_attr "mode" "V4SF,V4SF,V2SF,V2SF")])
3769
3770 (define_expand "vec_init<mode>"
3771   [(match_operand:V_128 0 "register_operand" "")
3772    (match_operand 1 "" "")]
3773   "TARGET_SSE"
3774 {
3775   ix86_expand_vector_init (false, operands[0], operands[1]);
3776   DONE;
3777 })
3778
3779 ;; Avoid combining registers from different units in a single alternative,
3780 ;; see comment above inline_secondary_memory_needed function in i386.c
3781 (define_insn "vec_set<mode>_0"
3782   [(set (match_operand:VI4F_128 0 "nonimmediate_operand"
3783           "=x,x,x ,x,x,x,x  ,x  ,m,m ,m")
3784         (vec_merge:VI4F_128
3785           (vec_duplicate:VI4F_128
3786             (match_operand:<ssescalarmode> 2 "general_operand"
3787           " x,m,*r,m,x,x,*rm,*rm,x,fF,*r"))
3788           (match_operand:VI4F_128 1 "vector_move_operand"
3789           " C,C,C ,C,0,x,0  ,x  ,0,0 ,0")
3790           (const_int 1)))]
3791   "TARGET_SSE"
3792   "@
3793    %vinsertps\t{$0xe, %d2, %0|%0, %d2, 0xe}
3794    %vmov<ssescalarmodesuffix>\t{%2, %0|%0, %2}
3795    %vmovd\t{%2, %0|%0, %2}
3796    movss\t{%2, %0|%0, %2}
3797    movss\t{%2, %0|%0, %2}
3798    vmovss\t{%2, %1, %0|%0, %1, %2}
3799    pinsrd\t{$0, %2, %0|%0, %2, 0}
3800    vpinsrd\t{$0, %2, %1, %0|%0, %1, %2, 0}
3801    #
3802    #
3803    #"
3804   [(set_attr "isa" "sse4,sse2,sse2,noavx,noavx,avx,sse4_noavx,avx,*,*,*")
3805    (set (attr "type")
3806      (cond [(eq_attr "alternative" "0,6,7")
3807               (const_string "sselog")
3808             (eq_attr "alternative" "9")
3809               (const_string "fmov")
3810             (eq_attr "alternative" "10")
3811               (const_string "imov")
3812            ]
3813            (const_string "ssemov")))
3814    (set_attr "prefix_extra" "*,*,*,*,*,*,1,1,*,*,*")
3815    (set_attr "length_immediate" "*,*,*,*,*,*,1,1,*,*,*")
3816    (set_attr "prefix" "maybe_vex,maybe_vex,maybe_vex,orig,orig,vex,orig,vex,*,*,*")
3817    (set_attr "mode" "SF,<ssescalarmode>,SI,SF,SF,SF,TI,TI,*,*,*")])
3818
3819 ;; A subset is vec_setv4sf.
3820 (define_insn "*vec_setv4sf_sse4_1"
3821   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
3822         (vec_merge:V4SF
3823           (vec_duplicate:V4SF
3824             (match_operand:SF 2 "nonimmediate_operand" "xm,xm"))
3825           (match_operand:V4SF 1 "register_operand" "0,x")
3826           (match_operand:SI 3 "const_int_operand" "")))]
3827   "TARGET_SSE4_1
3828    && ((unsigned) exact_log2 (INTVAL (operands[3]))
3829        < GET_MODE_NUNITS (V4SFmode))"
3830 {
3831   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])) << 4);
3832   switch (which_alternative)
3833     {
3834     case 0:
3835       return "insertps\t{%3, %2, %0|%0, %2, %3}";
3836     case 1:
3837       return "vinsertps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3838     default:
3839       gcc_unreachable ();
3840     }
3841 }
3842   [(set_attr "isa" "noavx,avx")
3843    (set_attr "type" "sselog")
3844    (set_attr "prefix_data16" "1,*")
3845    (set_attr "prefix_extra" "1")
3846    (set_attr "length_immediate" "1")
3847    (set_attr "prefix" "orig,vex")
3848    (set_attr "mode" "V4SF")])
3849
3850 (define_insn "sse4_1_insertps"
3851   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
3852         (unspec:V4SF [(match_operand:V4SF 2 "nonimmediate_operand" "xm,xm")
3853                       (match_operand:V4SF 1 "register_operand" "0,x")
3854                       (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
3855                      UNSPEC_INSERTPS))]
3856   "TARGET_SSE4_1"
3857 {
3858   if (MEM_P (operands[2]))
3859     {
3860       unsigned count_s = INTVAL (operands[3]) >> 6;
3861       if (count_s)
3862         operands[3] = GEN_INT (INTVAL (operands[3]) & 0x3f);
3863       operands[2] = adjust_address_nv (operands[2], SFmode, count_s * 4);
3864     }
3865   switch (which_alternative)
3866     {
3867     case 0:
3868       return "insertps\t{%3, %2, %0|%0, %2, %3}";
3869     case 1:
3870       return "vinsertps\t{%3, %2, %1, %0|%0, %1, %2, %3}";
3871     default:
3872       gcc_unreachable ();
3873     }
3874 }
3875   [(set_attr "isa" "noavx,avx")
3876    (set_attr "type" "sselog")
3877    (set_attr "prefix_data16" "1,*")
3878    (set_attr "prefix_extra" "1")
3879    (set_attr "length_immediate" "1")
3880    (set_attr "prefix" "orig,vex")
3881    (set_attr "mode" "V4SF")])
3882
3883 (define_split
3884   [(set (match_operand:VI4F_128 0 "memory_operand" "")
3885         (vec_merge:VI4F_128
3886           (vec_duplicate:VI4F_128
3887             (match_operand:<ssescalarmode> 1 "nonmemory_operand" ""))
3888           (match_dup 0)
3889           (const_int 1)))]
3890   "TARGET_SSE && reload_completed"
3891   [(const_int 0)]
3892 {
3893   emit_move_insn (adjust_address (operands[0], <ssescalarmode>mode, 0),
3894                   operands[1]);
3895   DONE;
3896 })
3897
3898 (define_expand "vec_set<mode>"
3899   [(match_operand:V 0 "register_operand" "")
3900    (match_operand:<ssescalarmode> 1 "register_operand" "")
3901    (match_operand 2 "const_int_operand" "")]
3902   "TARGET_SSE"
3903 {
3904   ix86_expand_vector_set (false, operands[0], operands[1],
3905                           INTVAL (operands[2]));
3906   DONE;
3907 })
3908
3909 (define_insn_and_split "*vec_extractv4sf_0"
3910   [(set (match_operand:SF 0 "nonimmediate_operand" "=x,m,f,r")
3911         (vec_select:SF
3912           (match_operand:V4SF 1 "nonimmediate_operand" "xm,x,m,m")
3913           (parallel [(const_int 0)])))]
3914   "TARGET_SSE && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3915   "#"
3916   "&& reload_completed"
3917   [(const_int 0)]
3918 {
3919   rtx op1 = operands[1];
3920   if (REG_P (op1))
3921     op1 = gen_rtx_REG (SFmode, REGNO (op1));
3922   else
3923     op1 = gen_lowpart (SFmode, op1);
3924   emit_move_insn (operands[0], op1);
3925   DONE;
3926 })
3927
3928 (define_insn_and_split "*sse4_1_extractps"
3929   [(set (match_operand:SF 0 "nonimmediate_operand" "=rm,x,x")
3930         (vec_select:SF
3931           (match_operand:V4SF 1 "register_operand" "x,0,x")
3932           (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n,n,n")])))]
3933   "TARGET_SSE4_1"
3934   "@
3935    %vextractps\t{%2, %1, %0|%0, %1, %2}
3936    #
3937    #"
3938   "&& reload_completed && SSE_REG_P (operands[0])"
3939   [(const_int 0)]
3940 {
3941   rtx dest = gen_rtx_REG (V4SFmode, REGNO (operands[0]));
3942   switch (INTVAL (operands[2]))
3943     {
3944     case 1:
3945     case 3:
3946       emit_insn (gen_sse_shufps_v4sf (dest, operands[1], operands[1],
3947                                       operands[2], operands[2],
3948                                       GEN_INT (INTVAL (operands[2]) + 4),
3949                                       GEN_INT (INTVAL (operands[2]) + 4)));
3950       break;
3951     case 2:
3952       emit_insn (gen_vec_interleave_highv4sf (dest, operands[1], operands[1]));
3953       break;
3954     default:
3955       /* 0 should be handled by the *vec_extractv4sf_0 pattern above.  */
3956       gcc_unreachable ();
3957     }
3958   DONE;
3959 }
3960   [(set_attr "isa" "*,noavx,avx")
3961    (set_attr "type" "sselog,*,*")
3962    (set_attr "prefix_data16" "1,*,*")
3963    (set_attr "prefix_extra" "1,*,*")
3964    (set_attr "length_immediate" "1,*,*")
3965    (set_attr "prefix" "maybe_vex,*,*")
3966    (set_attr "mode" "V4SF,*,*")])
3967
3968 (define_insn_and_split "*vec_extract_v4sf_mem"
3969   [(set (match_operand:SF 0 "register_operand" "=x,*r,f")
3970        (vec_select:SF
3971          (match_operand:V4SF 1 "memory_operand" "o,o,o")
3972          (parallel [(match_operand 2 "const_0_to_3_operand" "n,n,n")])))]
3973   "TARGET_SSE"
3974   "#"
3975   "&& reload_completed"
3976   [(const_int 0)]
3977 {
3978   int i = INTVAL (operands[2]);
3979
3980   emit_move_insn (operands[0], adjust_address (operands[1], SFmode, i*4));
3981   DONE;
3982 })
3983
3984 (define_expand "avx_vextractf128<mode>"
3985   [(match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "")
3986    (match_operand:V_256 1 "register_operand" "")
3987    (match_operand:SI 2 "const_0_to_1_operand" "")]
3988   "TARGET_AVX"
3989 {
3990   rtx (*insn)(rtx, rtx);
3991
3992   switch (INTVAL (operands[2]))
3993     {
3994     case 0:
3995       insn = gen_vec_extract_lo_<mode>;
3996       break;
3997     case 1:
3998       insn = gen_vec_extract_hi_<mode>;
3999       break;
4000     default:
4001       gcc_unreachable ();
4002     }
4003
4004   emit_insn (insn (operands[0], operands[1]));
4005   DONE;
4006 })
4007
4008 (define_insn_and_split "vec_extract_lo_<mode>"
4009   [(set (match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "=x,m")
4010         (vec_select:<ssehalfvecmode>
4011           (match_operand:VI8F_256 1 "nonimmediate_operand" "xm,x")
4012           (parallel [(const_int 0) (const_int 1)])))]
4013   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4014   "#"
4015   "&& reload_completed"
4016   [(const_int 0)]
4017 {
4018   rtx op1 = operands[1];
4019   if (REG_P (op1))
4020     op1 = gen_rtx_REG (<ssehalfvecmode>mode, REGNO (op1));
4021   else
4022     op1 = gen_lowpart (<ssehalfvecmode>mode, op1);
4023   emit_move_insn (operands[0], op1);
4024   DONE;
4025 })
4026
4027 (define_insn "vec_extract_hi_<mode>"
4028   [(set (match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "=x,m")
4029         (vec_select:<ssehalfvecmode>
4030           (match_operand:VI8F_256 1 "register_operand" "x,x")
4031           (parallel [(const_int 2) (const_int 3)])))]
4032   "TARGET_AVX"
4033   "vextract<i128>\t{$0x1, %1, %0|%0, %1, 0x1}"
4034   [(set_attr "type" "sselog")
4035    (set_attr "prefix_extra" "1")
4036    (set_attr "length_immediate" "1")
4037    (set_attr "memory" "none,store")
4038    (set_attr "prefix" "vex")
4039    (set_attr "mode" "<sseinsnmode>")])
4040
4041 (define_insn_and_split "vec_extract_lo_<mode>"
4042   [(set (match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "=x,m")
4043         (vec_select:<ssehalfvecmode>
4044           (match_operand:VI4F_256 1 "nonimmediate_operand" "xm,x")
4045           (parallel [(const_int 0) (const_int 1)
4046                      (const_int 2) (const_int 3)])))]
4047   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4048   "#"
4049   "&& reload_completed"
4050   [(const_int 0)]
4051 {
4052   rtx op1 = operands[1];
4053   if (REG_P (op1))
4054     op1 = gen_rtx_REG (<ssehalfvecmode>mode, REGNO (op1));
4055   else
4056     op1 = gen_lowpart (<ssehalfvecmode>mode, op1);
4057   emit_move_insn (operands[0], op1);
4058   DONE;
4059 })
4060
4061 (define_insn "vec_extract_hi_<mode>"
4062   [(set (match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "=x,m")
4063         (vec_select:<ssehalfvecmode>
4064           (match_operand:VI4F_256 1 "register_operand" "x,x")
4065           (parallel [(const_int 4) (const_int 5)
4066                      (const_int 6) (const_int 7)])))]
4067   "TARGET_AVX"
4068   "vextract<i128>\t{$0x1, %1, %0|%0, %1, 0x1}"
4069   [(set_attr "type" "sselog")
4070    (set_attr "prefix_extra" "1")
4071    (set_attr "length_immediate" "1")
4072    (set_attr "memory" "none,store")
4073    (set_attr "prefix" "vex")
4074    (set_attr "mode" "<sseinsnmode>")])
4075
4076 (define_insn_and_split "vec_extract_lo_v16hi"
4077   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=x,m")
4078         (vec_select:V8HI
4079           (match_operand:V16HI 1 "nonimmediate_operand" "xm,x")
4080           (parallel [(const_int 0) (const_int 1)
4081                      (const_int 2) (const_int 3)
4082                      (const_int 4) (const_int 5)
4083                      (const_int 6) (const_int 7)])))]
4084   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4085   "#"
4086   "&& reload_completed"
4087   [(const_int 0)]
4088 {
4089   rtx op1 = operands[1];
4090   if (REG_P (op1))
4091     op1 = gen_rtx_REG (V8HImode, REGNO (op1));
4092   else
4093     op1 = gen_lowpart (V8HImode, op1);
4094   emit_move_insn (operands[0], op1);
4095   DONE;
4096 })
4097
4098 (define_insn "vec_extract_hi_v16hi"
4099   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=x,m")
4100         (vec_select:V8HI
4101           (match_operand:V16HI 1 "register_operand" "x,x")
4102           (parallel [(const_int 8) (const_int 9)
4103                      (const_int 10) (const_int 11)
4104                      (const_int 12) (const_int 13)
4105                      (const_int 14) (const_int 15)])))]
4106   "TARGET_AVX"
4107   "vextract%~128\t{$0x1, %1, %0|%0, %1, 0x1}"
4108   [(set_attr "type" "sselog")
4109    (set_attr "prefix_extra" "1")
4110    (set_attr "length_immediate" "1")
4111    (set_attr "memory" "none,store")
4112    (set_attr "prefix" "vex")
4113    (set_attr "mode" "OI")])
4114
4115 (define_insn_and_split "vec_extract_lo_v32qi"
4116   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
4117         (vec_select:V16QI
4118           (match_operand:V32QI 1 "nonimmediate_operand" "xm,x")
4119           (parallel [(const_int 0) (const_int 1)
4120                      (const_int 2) (const_int 3)
4121                      (const_int 4) (const_int 5)
4122                      (const_int 6) (const_int 7)
4123                      (const_int 8) (const_int 9)
4124                      (const_int 10) (const_int 11)
4125                      (const_int 12) (const_int 13)
4126                      (const_int 14) (const_int 15)])))]
4127   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4128   "#"
4129   "&& reload_completed"
4130   [(const_int 0)]
4131 {
4132   rtx op1 = operands[1];
4133   if (REG_P (op1))
4134     op1 = gen_rtx_REG (V16QImode, REGNO (op1));
4135   else
4136     op1 = gen_lowpart (V16QImode, op1);
4137   emit_move_insn (operands[0], op1);
4138   DONE;
4139 })
4140
4141 (define_insn "vec_extract_hi_v32qi"
4142   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
4143         (vec_select:V16QI
4144           (match_operand:V32QI 1 "register_operand" "x,x")
4145           (parallel [(const_int 16) (const_int 17)
4146                      (const_int 18) (const_int 19)
4147                      (const_int 20) (const_int 21)
4148                      (const_int 22) (const_int 23)
4149                      (const_int 24) (const_int 25)
4150                      (const_int 26) (const_int 27)
4151                      (const_int 28) (const_int 29)
4152                      (const_int 30) (const_int 31)])))]
4153   "TARGET_AVX"
4154   "vextract%~128\t{$0x1, %1, %0|%0, %1, 0x1}"
4155   [(set_attr "type" "sselog")
4156    (set_attr "prefix_extra" "1")
4157    (set_attr "length_immediate" "1")
4158    (set_attr "memory" "none,store")
4159    (set_attr "prefix" "vex")
4160    (set_attr "mode" "OI")])
4161
4162 ;; Modes handled by vec_extract patterns.
4163 (define_mode_iterator VEC_EXTRACT_MODE
4164   [(V32QI "TARGET_AVX") V16QI
4165    (V16HI "TARGET_AVX") V8HI
4166    (V8SI "TARGET_AVX") V4SI
4167    (V4DI "TARGET_AVX") V2DI
4168    (V8SF "TARGET_AVX") V4SF
4169    (V4DF "TARGET_AVX") V2DF])
4170
4171 (define_expand "vec_extract<mode>"
4172   [(match_operand:<ssescalarmode> 0 "register_operand" "")
4173    (match_operand:VEC_EXTRACT_MODE 1 "register_operand" "")
4174    (match_operand 2 "const_int_operand" "")]
4175   "TARGET_SSE"
4176 {
4177   ix86_expand_vector_extract (false, operands[0], operands[1],
4178                               INTVAL (operands[2]));
4179   DONE;
4180 })
4181
4182 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4183 ;;
4184 ;; Parallel double-precision floating point element swizzling
4185 ;;
4186 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4187
4188 ;; Recall that the 256-bit unpck insns only shuffle within their lanes.
4189 (define_insn "avx_unpckhpd256"
4190   [(set (match_operand:V4DF 0 "register_operand" "=x")
4191         (vec_select:V4DF
4192           (vec_concat:V8DF
4193             (match_operand:V4DF 1 "register_operand" "x")
4194             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4195           (parallel [(const_int 1) (const_int 5)
4196                      (const_int 3) (const_int 7)])))]
4197   "TARGET_AVX"
4198   "vunpckhpd\t{%2, %1, %0|%0, %1, %2}"
4199   [(set_attr "type" "sselog")
4200    (set_attr "prefix" "vex")
4201    (set_attr "mode" "V4DF")])
4202
4203 (define_expand "vec_interleave_highv4df"
4204   [(set (match_dup 3)
4205         (vec_select:V4DF
4206           (vec_concat:V8DF
4207             (match_operand:V4DF 1 "register_operand" "x")
4208             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4209           (parallel [(const_int 0) (const_int 4)
4210                      (const_int 2) (const_int 6)])))
4211    (set (match_dup 4)
4212         (vec_select:V4DF
4213           (vec_concat:V8DF
4214             (match_dup 1)
4215             (match_dup 2))
4216           (parallel [(const_int 1) (const_int 5)
4217                      (const_int 3) (const_int 7)])))
4218    (set (match_operand:V4DF 0 "register_operand" "")
4219         (vec_select:V4DF
4220           (vec_concat:V8DF
4221             (match_dup 3)
4222             (match_dup 4))
4223           (parallel [(const_int 2) (const_int 3)
4224                      (const_int 6) (const_int 7)])))]
4225  "TARGET_AVX"
4226 {
4227   operands[3] = gen_reg_rtx (V4DFmode);
4228   operands[4] = gen_reg_rtx (V4DFmode);
4229 })
4230
4231
4232 (define_expand "vec_interleave_highv2df"
4233   [(set (match_operand:V2DF 0 "register_operand" "")
4234         (vec_select:V2DF
4235           (vec_concat:V4DF
4236             (match_operand:V2DF 1 "nonimmediate_operand" "")
4237             (match_operand:V2DF 2 "nonimmediate_operand" ""))
4238           (parallel [(const_int 1)
4239                      (const_int 3)])))]
4240   "TARGET_SSE2"
4241 {
4242   if (!ix86_vec_interleave_v2df_operator_ok (operands, 1))
4243     operands[2] = force_reg (V2DFmode, operands[2]);
4244 })
4245
4246 (define_insn "*vec_interleave_highv2df"
4247   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,x,x,x,m")
4248         (vec_select:V2DF
4249           (vec_concat:V4DF
4250             (match_operand:V2DF 1 "nonimmediate_operand" " 0,x,o,o,o,x")
4251             (match_operand:V2DF 2 "nonimmediate_operand" " x,x,1,0,x,0"))
4252           (parallel [(const_int 1)
4253                      (const_int 3)])))]
4254   "TARGET_SSE2 && ix86_vec_interleave_v2df_operator_ok (operands, 1)"
4255   "@
4256    unpckhpd\t{%2, %0|%0, %2}
4257    vunpckhpd\t{%2, %1, %0|%0, %1, %2}
4258    %vmovddup\t{%H1, %0|%0, %H1}
4259    movlpd\t{%H1, %0|%0, %H1}
4260    vmovlpd\t{%H1, %2, %0|%0, %2, %H1}
4261    %vmovhpd\t{%1, %0|%0, %1}"
4262   [(set_attr "isa" "noavx,avx,sse3,noavx,avx,*")
4263   (set_attr "type" "sselog,sselog,sselog,ssemov,ssemov,ssemov")
4264    (set_attr "prefix_data16" "*,*,*,1,*,1")
4265    (set_attr "prefix" "orig,vex,maybe_vex,orig,vex,maybe_vex")
4266    (set_attr "mode" "V2DF,V2DF,V2DF,V1DF,V1DF,V1DF")])
4267
4268 ;; Recall that the 256-bit unpck insns only shuffle within their lanes.
4269 (define_expand "avx_movddup256"
4270   [(set (match_operand:V4DF 0 "register_operand" "")
4271         (vec_select:V4DF
4272           (vec_concat:V8DF
4273             (match_operand:V4DF 1 "nonimmediate_operand" "")
4274             (match_dup 1))
4275           (parallel [(const_int 0) (const_int 4)
4276                      (const_int 2) (const_int 6)])))]
4277   "TARGET_AVX")
4278
4279 (define_expand "avx_unpcklpd256"
4280   [(set (match_operand:V4DF 0 "register_operand" "")
4281         (vec_select:V4DF
4282           (vec_concat:V8DF
4283             (match_operand:V4DF 1 "register_operand" "")
4284             (match_operand:V4DF 2 "nonimmediate_operand" ""))
4285           (parallel [(const_int 0) (const_int 4)
4286                      (const_int 2) (const_int 6)])))]
4287   "TARGET_AVX")
4288
4289 (define_insn "*avx_unpcklpd256"
4290   [(set (match_operand:V4DF 0 "register_operand"         "=x,x")
4291         (vec_select:V4DF
4292           (vec_concat:V8DF
4293             (match_operand:V4DF 1 "nonimmediate_operand" " x,m")
4294             (match_operand:V4DF 2 "nonimmediate_operand" "xm,1"))
4295           (parallel [(const_int 0) (const_int 4)
4296                      (const_int 2) (const_int 6)])))]
4297   "TARGET_AVX"
4298   "@
4299    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4300    vmovddup\t{%1, %0|%0, %1}"
4301   [(set_attr "type" "sselog")
4302    (set_attr "prefix" "vex")
4303    (set_attr "mode" "V4DF")])
4304
4305 (define_expand "vec_interleave_lowv4df"
4306   [(set (match_dup 3)
4307         (vec_select:V4DF
4308           (vec_concat:V8DF
4309             (match_operand:V4DF 1 "register_operand" "x")
4310             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4311           (parallel [(const_int 0) (const_int 4)
4312                      (const_int 2) (const_int 6)])))
4313    (set (match_dup 4)
4314         (vec_select:V4DF
4315           (vec_concat:V8DF
4316             (match_dup 1)
4317             (match_dup 2))
4318           (parallel [(const_int 1) (const_int 5)
4319                      (const_int 3) (const_int 7)])))
4320    (set (match_operand:V4DF 0 "register_operand" "")
4321         (vec_select:V4DF
4322           (vec_concat:V8DF
4323             (match_dup 3)
4324             (match_dup 4))
4325           (parallel [(const_int 0) (const_int 1)
4326                      (const_int 4) (const_int 5)])))]
4327  "TARGET_AVX"
4328 {
4329   operands[3] = gen_reg_rtx (V4DFmode);
4330   operands[4] = gen_reg_rtx (V4DFmode);
4331 })
4332
4333 (define_expand "vec_interleave_lowv2df"
4334   [(set (match_operand:V2DF 0 "register_operand" "")
4335         (vec_select:V2DF
4336           (vec_concat:V4DF
4337             (match_operand:V2DF 1 "nonimmediate_operand" "")
4338             (match_operand:V2DF 2 "nonimmediate_operand" ""))
4339           (parallel [(const_int 0)
4340                      (const_int 2)])))]
4341   "TARGET_SSE2"
4342 {
4343   if (!ix86_vec_interleave_v2df_operator_ok (operands, 0))
4344     operands[1] = force_reg (V2DFmode, operands[1]);
4345 })
4346
4347 (define_insn "*vec_interleave_lowv2df"
4348   [(set (match_operand:V2DF 0 "nonimmediate_operand"     "=x,x,x,x,x,o")
4349         (vec_select:V2DF
4350           (vec_concat:V4DF
4351             (match_operand:V2DF 1 "nonimmediate_operand" " 0,x,m,0,x,0")
4352             (match_operand:V2DF 2 "nonimmediate_operand" " x,x,1,m,m,x"))
4353           (parallel [(const_int 0)
4354                      (const_int 2)])))]
4355   "TARGET_SSE2 && ix86_vec_interleave_v2df_operator_ok (operands, 0)"
4356   "@
4357    unpcklpd\t{%2, %0|%0, %2}
4358    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4359    %vmovddup\t{%1, %0|%0, %1}
4360    movhpd\t{%2, %0|%0, %2}
4361    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4362    %vmovlpd\t{%2, %H0|%H0, %2}"
4363   [(set_attr "isa" "noavx,avx,sse3,noavx,avx,*")
4364    (set_attr "type" "sselog,sselog,sselog,ssemov,ssemov,ssemov")
4365    (set_attr "prefix_data16" "*,*,*,1,*,1")
4366    (set_attr "prefix" "orig,vex,maybe_vex,orig,vex,maybe_vex")
4367    (set_attr "mode" "V2DF,V2DF,V2DF,V1DF,V1DF,V1DF")])
4368
4369 (define_split
4370   [(set (match_operand:V2DF 0 "memory_operand" "")
4371         (vec_select:V2DF
4372           (vec_concat:V4DF
4373             (match_operand:V2DF 1 "register_operand" "")
4374             (match_dup 1))
4375           (parallel [(const_int 0)
4376                      (const_int 2)])))]
4377   "TARGET_SSE3 && reload_completed"
4378   [(const_int 0)]
4379 {
4380   rtx low = gen_rtx_REG (DFmode, REGNO (operands[1]));
4381   emit_move_insn (adjust_address (operands[0], DFmode, 0), low);
4382   emit_move_insn (adjust_address (operands[0], DFmode, 8), low);
4383   DONE;
4384 })
4385
4386 (define_split
4387   [(set (match_operand:V2DF 0 "register_operand" "")
4388         (vec_select:V2DF
4389           (vec_concat:V4DF
4390             (match_operand:V2DF 1 "memory_operand" "")
4391             (match_dup 1))
4392           (parallel [(match_operand:SI 2 "const_0_to_1_operand" "")
4393                      (match_operand:SI 3 "const_int_operand" "")])))]
4394   "TARGET_SSE3 && INTVAL (operands[2]) + 2 == INTVAL (operands[3])"
4395   [(set (match_dup 0) (vec_duplicate:V2DF (match_dup 1)))]
4396 {
4397   operands[1] = adjust_address (operands[1], DFmode, INTVAL (operands[2]) * 8);
4398 })
4399
4400 (define_expand "avx_shufpd256"
4401   [(match_operand:V4DF 0 "register_operand" "")
4402    (match_operand:V4DF 1 "register_operand" "")
4403    (match_operand:V4DF 2 "nonimmediate_operand" "")
4404    (match_operand:SI 3 "const_int_operand" "")]
4405   "TARGET_AVX"
4406 {
4407   int mask = INTVAL (operands[3]);
4408   emit_insn (gen_avx_shufpd256_1 (operands[0], operands[1], operands[2],
4409                                    GEN_INT (mask & 1),
4410                                    GEN_INT (mask & 2 ? 5 : 4),
4411                                    GEN_INT (mask & 4 ? 3 : 2),
4412                                    GEN_INT (mask & 8 ? 7 : 6)));
4413   DONE;
4414 })
4415
4416 (define_insn "avx_shufpd256_1"
4417   [(set (match_operand:V4DF 0 "register_operand" "=x")
4418         (vec_select:V4DF
4419           (vec_concat:V8DF
4420             (match_operand:V4DF 1 "register_operand" "x")
4421             (match_operand:V4DF 2 "nonimmediate_operand" "xm"))
4422           (parallel [(match_operand 3 "const_0_to_1_operand" "")
4423                      (match_operand 4 "const_4_to_5_operand" "")
4424                      (match_operand 5 "const_2_to_3_operand" "")
4425                      (match_operand 6 "const_6_to_7_operand" "")])))]
4426   "TARGET_AVX"
4427 {
4428   int mask;
4429   mask = INTVAL (operands[3]);
4430   mask |= (INTVAL (operands[4]) - 4) << 1;
4431   mask |= (INTVAL (operands[5]) - 2) << 2;
4432   mask |= (INTVAL (operands[6]) - 6) << 3;
4433   operands[3] = GEN_INT (mask);
4434
4435   return "vshufpd\t{%3, %2, %1, %0|%0, %1, %2, %3}";
4436 }
4437   [(set_attr "type" "sselog")
4438    (set_attr "length_immediate" "1")
4439    (set_attr "prefix" "vex")
4440    (set_attr "mode" "V4DF")])
4441
4442 (define_expand "sse2_shufpd"
4443   [(match_operand:V2DF 0 "register_operand" "")
4444    (match_operand:V2DF 1 "register_operand" "")
4445    (match_operand:V2DF 2 "nonimmediate_operand" "")
4446    (match_operand:SI 3 "const_int_operand" "")]
4447   "TARGET_SSE2"
4448 {
4449   int mask = INTVAL (operands[3]);
4450   emit_insn (gen_sse2_shufpd_v2df (operands[0], operands[1], operands[2],
4451                                 GEN_INT (mask & 1),
4452                                 GEN_INT (mask & 2 ? 3 : 2)));
4453   DONE;
4454 })
4455
4456 ;; punpcklqdq and punpckhqdq are shorter than shufpd.
4457 (define_insn "avx2_interleave_highv4di"
4458   [(set (match_operand:V4DI 0 "register_operand" "=x")
4459         (vec_select:V4DI
4460           (vec_concat:V8DI
4461             (match_operand:V4DI 1 "register_operand" "x")
4462             (match_operand:V4DI 2 "nonimmediate_operand" "xm"))
4463           (parallel [(const_int 1)
4464                      (const_int 5)
4465                      (const_int 3)
4466                      (const_int 7)])))]
4467   "TARGET_AVX2"
4468   "vpunpckhqdq\t{%2, %1, %0|%0, %1, %2}"
4469   [(set_attr "type" "sselog")
4470    (set_attr "prefix" "vex")
4471    (set_attr "mode" "OI")])
4472
4473 (define_insn "vec_interleave_highv2di"
4474   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
4475         (vec_select:V2DI
4476           (vec_concat:V4DI
4477             (match_operand:V2DI 1 "register_operand" "0,x")
4478             (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm"))
4479           (parallel [(const_int 1)
4480                      (const_int 3)])))]
4481   "TARGET_SSE2"
4482   "@
4483    punpckhqdq\t{%2, %0|%0, %2}
4484    vpunpckhqdq\t{%2, %1, %0|%0, %1, %2}"
4485   [(set_attr "isa" "noavx,avx")
4486    (set_attr "type" "sselog")
4487    (set_attr "prefix_data16" "1,*")
4488    (set_attr "prefix" "orig,vex")
4489    (set_attr "mode" "TI")])
4490
4491 (define_insn "avx2_interleave_lowv4di"
4492   [(set (match_operand:V4DI 0 "register_operand" "=x")
4493         (vec_select:V4DI
4494           (vec_concat:V8DI
4495             (match_operand:V4DI 1 "register_operand" "x")
4496             (match_operand:V4DI 2 "nonimmediate_operand" "xm"))
4497           (parallel [(const_int 0)
4498                      (const_int 4)
4499                      (const_int 2)
4500                      (const_int 6)])))]
4501   "TARGET_AVX2"
4502   "vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}"
4503   [(set_attr "type" "sselog")
4504    (set_attr "prefix" "vex")
4505    (set_attr "mode" "OI")])
4506
4507 (define_insn "vec_interleave_lowv2di"
4508   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
4509         (vec_select:V2DI
4510           (vec_concat:V4DI
4511             (match_operand:V2DI 1 "register_operand" "0,x")
4512             (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm"))
4513           (parallel [(const_int 0)
4514                      (const_int 2)])))]
4515   "TARGET_SSE2"
4516   "@
4517    punpcklqdq\t{%2, %0|%0, %2}
4518    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}"
4519   [(set_attr "isa" "noavx,avx")
4520    (set_attr "type" "sselog")
4521    (set_attr "prefix_data16" "1,*")
4522    (set_attr "prefix" "orig,vex")
4523    (set_attr "mode" "TI")])
4524
4525 (define_insn "sse2_shufpd_<mode>"
4526   [(set (match_operand:VI8F_128 0 "register_operand" "=x,x")
4527         (vec_select:VI8F_128
4528           (vec_concat:<ssedoublevecmode>
4529             (match_operand:VI8F_128 1 "register_operand" "0,x")
4530             (match_operand:VI8F_128 2 "nonimmediate_operand" "xm,xm"))
4531           (parallel [(match_operand 3 "const_0_to_1_operand" "")
4532                      (match_operand 4 "const_2_to_3_operand" "")])))]
4533   "TARGET_SSE2"
4534 {
4535   int mask;
4536   mask = INTVAL (operands[3]);
4537   mask |= (INTVAL (operands[4]) - 2) << 1;
4538   operands[3] = GEN_INT (mask);
4539
4540   switch (which_alternative)
4541     {
4542     case 0:
4543       return "shufpd\t{%3, %2, %0|%0, %2, %3}";
4544     case 1:
4545       return "vshufpd\t{%3, %2, %1, %0|%0, %1, %2, %3}";
4546     default:
4547       gcc_unreachable ();
4548     }
4549 }
4550   [(set_attr "isa" "noavx,avx")
4551    (set_attr "type" "sselog")
4552    (set_attr "length_immediate" "1")
4553    (set_attr "prefix" "orig,vex")
4554    (set_attr "mode" "V2DF")])
4555
4556 ;; Avoid combining registers from different units in a single alternative,
4557 ;; see comment above inline_secondary_memory_needed function in i386.c
4558 (define_insn "sse2_storehpd"
4559   [(set (match_operand:DF 0 "nonimmediate_operand"     "=m,x,x,x,*f,r")
4560         (vec_select:DF
4561           (match_operand:V2DF 1 "nonimmediate_operand" " x,0,x,o,o,o")
4562           (parallel [(const_int 1)])))]
4563   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4564   "@
4565    %vmovhpd\t{%1, %0|%0, %1}
4566    unpckhpd\t%0, %0
4567    vunpckhpd\t{%d1, %0|%0, %d1}
4568    #
4569    #
4570    #"
4571   [(set_attr "isa" "*,noavx,avx,*,*,*")
4572    (set_attr "type" "ssemov,sselog1,sselog1,ssemov,fmov,imov")
4573    (set (attr "prefix_data16")
4574      (if_then_else
4575        (and (eq_attr "alternative" "0")
4576             (not (match_test "TARGET_AVX")))
4577        (const_string "1")
4578        (const_string "*")))
4579    (set_attr "prefix" "maybe_vex,orig,vex,*,*,*")
4580    (set_attr "mode" "V1DF,V1DF,V2DF,DF,DF,DF")])
4581
4582 (define_split
4583   [(set (match_operand:DF 0 "register_operand" "")
4584         (vec_select:DF
4585           (match_operand:V2DF 1 "memory_operand" "")
4586           (parallel [(const_int 1)])))]
4587   "TARGET_SSE2 && reload_completed"
4588   [(set (match_dup 0) (match_dup 1))]
4589   "operands[1] = adjust_address (operands[1], DFmode, 8);")
4590
4591 (define_insn "*vec_extractv2df_1_sse"
4592   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,x,x")
4593         (vec_select:DF
4594           (match_operand:V2DF 1 "nonimmediate_operand" "x,x,o")
4595           (parallel [(const_int 1)])))]
4596   "!TARGET_SSE2 && TARGET_SSE
4597    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4598   "@
4599    movhps\t{%1, %0|%0, %1}
4600    movhlps\t{%1, %0|%0, %1}
4601    movlps\t{%H1, %0|%0, %H1}"
4602   [(set_attr "type" "ssemov")
4603    (set_attr "mode" "V2SF,V4SF,V2SF")])
4604
4605 ;; Avoid combining registers from different units in a single alternative,
4606 ;; see comment above inline_secondary_memory_needed function in i386.c
4607 (define_insn "sse2_storelpd"
4608   [(set (match_operand:DF 0 "nonimmediate_operand"     "=m,x,x,*f,r")
4609         (vec_select:DF
4610           (match_operand:V2DF 1 "nonimmediate_operand" " x,x,m,m,m")
4611           (parallel [(const_int 0)])))]
4612   "TARGET_SSE2 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4613   "@
4614    %vmovlpd\t{%1, %0|%0, %1}
4615    #
4616    #
4617    #
4618    #"
4619   [(set_attr "type" "ssemov,ssemov,ssemov,fmov,imov")
4620    (set_attr "prefix_data16" "1,*,*,*,*")
4621    (set_attr "prefix" "maybe_vex")
4622    (set_attr "mode" "V1DF,DF,DF,DF,DF")])
4623
4624 (define_split
4625   [(set (match_operand:DF 0 "register_operand" "")
4626         (vec_select:DF
4627           (match_operand:V2DF 1 "nonimmediate_operand" "")
4628           (parallel [(const_int 0)])))]
4629   "TARGET_SSE2 && reload_completed"
4630   [(const_int 0)]
4631 {
4632   rtx op1 = operands[1];
4633   if (REG_P (op1))
4634     op1 = gen_rtx_REG (DFmode, REGNO (op1));
4635   else
4636     op1 = gen_lowpart (DFmode, op1);
4637   emit_move_insn (operands[0], op1);
4638   DONE;
4639 })
4640
4641 (define_insn "*vec_extractv2df_0_sse"
4642   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,x,x")
4643         (vec_select:DF
4644           (match_operand:V2DF 1 "nonimmediate_operand" "x,x,m")
4645           (parallel [(const_int 0)])))]
4646   "!TARGET_SSE2 && TARGET_SSE
4647    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
4648   "@
4649    movlps\t{%1, %0|%0, %1}
4650    movaps\t{%1, %0|%0, %1}
4651    movlps\t{%1, %0|%0, %1}"
4652   [(set_attr "type" "ssemov")
4653    (set_attr "mode" "V2SF,V4SF,V2SF")])
4654
4655 (define_expand "sse2_loadhpd_exp"
4656   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
4657         (vec_concat:V2DF
4658           (vec_select:DF
4659             (match_operand:V2DF 1 "nonimmediate_operand" "")
4660             (parallel [(const_int 0)]))
4661           (match_operand:DF 2 "nonimmediate_operand" "")))]
4662   "TARGET_SSE2"
4663 {
4664   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);
4665
4666   emit_insn (gen_sse2_loadhpd (dst, operands[1], operands[2]));
4667
4668   /* Fix up the destination if needed.  */
4669   if (dst != operands[0])
4670     emit_move_insn (operands[0], dst);
4671
4672   DONE;
4673 })
4674
4675 ;; Avoid combining registers from different units in a single alternative,
4676 ;; see comment above inline_secondary_memory_needed function in i386.c
4677 (define_insn "sse2_loadhpd"
4678   [(set (match_operand:V2DF 0 "nonimmediate_operand"
4679           "=x,x,x,x,o,o ,o")
4680         (vec_concat:V2DF
4681           (vec_select:DF
4682             (match_operand:V2DF 1 "nonimmediate_operand"
4683           " 0,x,0,x,0,0 ,0")
4684             (parallel [(const_int 0)]))
4685           (match_operand:DF 2 "nonimmediate_operand"
4686           " m,m,x,x,x,*f,r")))]
4687   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4688   "@
4689    movhpd\t{%2, %0|%0, %2}
4690    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4691    unpcklpd\t{%2, %0|%0, %2}
4692    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4693    #
4694    #
4695    #"
4696   [(set_attr "isa" "noavx,avx,noavx,avx,*,*,*")
4697    (set_attr "type" "ssemov,ssemov,sselog,sselog,ssemov,fmov,imov")
4698    (set_attr "prefix_data16" "1,*,*,*,*,*,*")
4699    (set_attr "prefix" "orig,vex,orig,vex,*,*,*")
4700    (set_attr "mode" "V1DF,V1DF,V2DF,V2DF,DF,DF,DF")])
4701
4702 (define_split
4703   [(set (match_operand:V2DF 0 "memory_operand" "")
4704         (vec_concat:V2DF
4705           (vec_select:DF (match_dup 0) (parallel [(const_int 0)]))
4706           (match_operand:DF 1 "register_operand" "")))]
4707   "TARGET_SSE2 && reload_completed"
4708   [(set (match_dup 0) (match_dup 1))]
4709   "operands[0] = adjust_address (operands[0], DFmode, 8);")
4710
4711 (define_expand "sse2_loadlpd_exp"
4712   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
4713         (vec_concat:V2DF
4714           (match_operand:DF 2 "nonimmediate_operand" "")
4715           (vec_select:DF
4716             (match_operand:V2DF 1 "nonimmediate_operand" "")
4717             (parallel [(const_int 1)]))))]
4718   "TARGET_SSE2"
4719 {
4720   rtx dst = ix86_fixup_binary_operands (UNKNOWN, V2DFmode, operands);
4721
4722   emit_insn (gen_sse2_loadlpd (dst, operands[1], operands[2]));
4723
4724   /* Fix up the destination if needed.  */
4725   if (dst != operands[0])
4726     emit_move_insn (operands[0], dst);
4727
4728   DONE;
4729 })
4730
4731 ;; Avoid combining registers from different units in a single alternative,
4732 ;; see comment above inline_secondary_memory_needed function in i386.c
4733 (define_insn "sse2_loadlpd"
4734   [(set (match_operand:V2DF 0 "nonimmediate_operand"
4735           "=x,x,x,x,x,x,x,x,m,m ,m")
4736         (vec_concat:V2DF
4737           (match_operand:DF 2 "nonimmediate_operand"
4738           " m,m,m,x,x,0,0,x,x,*f,r")
4739           (vec_select:DF
4740             (match_operand:V2DF 1 "vector_move_operand"
4741           " C,0,x,0,x,x,o,o,0,0 ,0")
4742             (parallel [(const_int 1)]))))]
4743   "TARGET_SSE2 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
4744   "@
4745    %vmovsd\t{%2, %0|%0, %2}
4746    movlpd\t{%2, %0|%0, %2}
4747    vmovlpd\t{%2, %1, %0|%0, %1, %2}
4748    movsd\t{%2, %0|%0, %2}
4749    vmovsd\t{%2, %1, %0|%0, %1, %2}
4750    shufpd\t{$2, %1, %0|%0, %1, 2}
4751    movhpd\t{%H1, %0|%0, %H1}
4752    vmovhpd\t{%H1, %2, %0|%0, %2, %H1}
4753    #
4754    #
4755    #"
4756   [(set_attr "isa" "*,noavx,avx,noavx,avx,noavx,noavx,avx,*,*,*")
4757    (set (attr "type")
4758      (cond [(eq_attr "alternative" "5")
4759               (const_string "sselog")
4760             (eq_attr "alternative" "9")
4761               (const_string "fmov")
4762             (eq_attr "alternative" "10")
4763               (const_string "imov")
4764            ]
4765            (const_string "ssemov")))
4766    (set_attr "prefix_data16" "*,1,*,*,*,*,1,*,*,*,*")
4767    (set_attr "length_immediate" "*,*,*,*,*,1,*,*,*,*,*")
4768    (set_attr "prefix" "maybe_vex,orig,vex,orig,vex,orig,orig,vex,*,*,*")
4769    (set_attr "mode" "DF,V1DF,V1DF,V1DF,V1DF,V2DF,V1DF,V1DF,DF,DF,DF")])
4770
4771 (define_split
4772   [(set (match_operand:V2DF 0 "memory_operand" "")
4773         (vec_concat:V2DF
4774           (match_operand:DF 1 "register_operand" "")
4775           (vec_select:DF (match_dup 0) (parallel [(const_int 1)]))))]
4776   "TARGET_SSE2 && reload_completed"
4777   [(set (match_dup 0) (match_dup 1))]
4778   "operands[0] = adjust_address (operands[0], DFmode, 8);")
4779
4780 (define_insn "sse2_movsd"
4781   [(set (match_operand:V2DF 0 "nonimmediate_operand"   "=x,x,x,x,m,x,x,x,o")
4782         (vec_merge:V2DF
4783           (match_operand:V2DF 2 "nonimmediate_operand" " x,x,m,m,x,0,0,x,0")
4784           (match_operand:V2DF 1 "nonimmediate_operand" " 0,x,0,x,0,x,o,o,x")
4785           (const_int 1)))]
4786   "TARGET_SSE2"
4787   "@
4788    movsd\t{%2, %0|%0, %2}
4789    vmovsd\t{%2, %1, %0|%0, %1, %2}
4790    movlpd\t{%2, %0|%0, %2}
4791    vmovlpd\t{%2, %1, %0|%0, %1, %2}
4792    %vmovlpd\t{%2, %0|%0, %2}
4793    shufpd\t{$2, %1, %0|%0, %1, 2}
4794    movhps\t{%H1, %0|%0, %H1}
4795    vmovhps\t{%H1, %2, %0|%0, %2, %H1}
4796    %vmovhps\t{%1, %H0|%H0, %1}"
4797   [(set_attr "isa" "noavx,avx,noavx,avx,*,noavx,noavx,avx,*")
4798    (set (attr "type")
4799      (if_then_else
4800        (eq_attr "alternative" "5")
4801        (const_string "sselog")
4802        (const_string "ssemov")))
4803    (set (attr "prefix_data16")
4804      (if_then_else
4805        (and (eq_attr "alternative" "2,4")
4806             (not (match_test "TARGET_AVX")))
4807        (const_string "1")
4808        (const_string "*")))
4809    (set_attr "length_immediate" "*,*,*,*,*,1,*,*,*")
4810    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex,orig,orig,vex,maybe_vex")
4811    (set_attr "mode" "DF,DF,V1DF,V1DF,V1DF,V2DF,V1DF,V1DF,V1DF")])
4812
4813 (define_insn "vec_dupv2df"
4814   [(set (match_operand:V2DF 0 "register_operand"     "=x,x")
4815         (vec_duplicate:V2DF
4816           (match_operand:DF 1 "nonimmediate_operand" " 0,xm")))]
4817   "TARGET_SSE2"
4818   "@
4819    unpcklpd\t%0, %0
4820    %vmovddup\t{%1, %0|%0, %1}"
4821   [(set_attr "isa" "noavx,sse3")
4822    (set_attr "type" "sselog1")
4823    (set_attr "prefix" "orig,maybe_vex")
4824    (set_attr "mode" "V2DF")])
4825
4826 (define_insn "*vec_concatv2df"
4827   [(set (match_operand:V2DF 0 "register_operand"     "=x,x,x,x,x,x,x,x")
4828         (vec_concat:V2DF
4829           (match_operand:DF 1 "nonimmediate_operand" " 0,x,m,0,x,m,0,0")
4830           (match_operand:DF 2 "vector_move_operand"  " x,x,1,m,m,C,x,m")))]
4831   "TARGET_SSE"
4832   "@
4833    unpcklpd\t{%2, %0|%0, %2}
4834    vunpcklpd\t{%2, %1, %0|%0, %1, %2}
4835    %vmovddup\t{%1, %0|%0, %1}
4836    movhpd\t{%2, %0|%0, %2}
4837    vmovhpd\t{%2, %1, %0|%0, %1, %2}
4838    %vmovsd\t{%1, %0|%0, %1}
4839    movlhps\t{%2, %0|%0, %2}
4840    movhps\t{%2, %0|%0, %2}"
4841   [(set_attr "isa" "sse2_noavx,avx,sse3,sse2_noavx,avx,sse2,noavx,noavx")
4842    (set (attr "type")
4843      (if_then_else
4844        (eq_attr "alternative" "0,1,2")
4845        (const_string "sselog")
4846        (const_string "ssemov")))
4847    (set_attr "prefix_data16" "*,*,*,1,*,*,*,*")
4848    (set_attr "prefix" "orig,vex,maybe_vex,orig,vex,maybe_vex,orig,orig")
4849    (set_attr "mode" "V2DF,V2DF,DF,V1DF,V1DF,DF,V4SF,V2SF")])
4850
4851 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4852 ;;
4853 ;; Parallel integral arithmetic
4854 ;;
4855 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
4856
4857 (define_expand "neg<mode>2"
4858   [(set (match_operand:VI_AVX2 0 "register_operand" "")
4859         (minus:VI_AVX2
4860           (match_dup 2)
4861           (match_operand:VI_AVX2 1 "nonimmediate_operand" "")))]
4862   "TARGET_SSE2"
4863   "operands[2] = force_reg (<MODE>mode, CONST0_RTX (<MODE>mode));")
4864
4865 (define_expand "<plusminus_insn><mode>3"
4866   [(set (match_operand:VI_AVX2 0 "register_operand" "")
4867         (plusminus:VI_AVX2
4868           (match_operand:VI_AVX2 1 "nonimmediate_operand" "")
4869           (match_operand:VI_AVX2 2 "nonimmediate_operand" "")))]
4870   "TARGET_SSE2"
4871   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
4872
4873 (define_insn "*<plusminus_insn><mode>3"
4874   [(set (match_operand:VI_AVX2 0 "register_operand" "=x,x")
4875         (plusminus:VI_AVX2
4876           (match_operand:VI_AVX2 1 "nonimmediate_operand" "<comm>0,x")
4877           (match_operand:VI_AVX2 2 "nonimmediate_operand" "xm,xm")))]
4878   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4879   "@
4880    p<plusminus_mnemonic><ssemodesuffix>\t{%2, %0|%0, %2}
4881    vp<plusminus_mnemonic><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
4882   [(set_attr "isa" "noavx,avx")
4883    (set_attr "type" "sseiadd")
4884    (set_attr "prefix_data16" "1,*")
4885    (set_attr "prefix" "orig,vex")
4886    (set_attr "mode" "<sseinsnmode>")])
4887
4888 (define_expand "<sse2_avx2>_<plusminus_insn><mode>3"
4889   [(set (match_operand:VI12_AVX2 0 "register_operand" "")
4890         (sat_plusminus:VI12_AVX2
4891           (match_operand:VI12_AVX2 1 "nonimmediate_operand" "")
4892           (match_operand:VI12_AVX2 2 "nonimmediate_operand" "")))]
4893   "TARGET_SSE2"
4894   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
4895
4896 (define_insn "*<sse2_avx2>_<plusminus_insn><mode>3"
4897   [(set (match_operand:VI12_AVX2 0 "register_operand" "=x,x")
4898         (sat_plusminus:VI12_AVX2
4899           (match_operand:VI12_AVX2 1 "nonimmediate_operand" "<comm>0,x")
4900           (match_operand:VI12_AVX2 2 "nonimmediate_operand" "xm,xm")))]
4901   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
4902   "@
4903    p<plusminus_mnemonic><ssemodesuffix>\t{%2, %0|%0, %2}
4904    vp<plusminus_mnemonic><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
4905   [(set_attr "isa" "noavx,avx")
4906    (set_attr "type" "sseiadd")
4907    (set_attr "prefix_data16" "1,*")
4908    (set_attr "prefix" "orig,vex")
4909    (set_attr "mode" "TI")])
4910
4911 (define_insn_and_split "mul<mode>3"
4912   [(set (match_operand:VI1_AVX2 0 "register_operand" "")
4913         (mult:VI1_AVX2 (match_operand:VI1_AVX2 1 "register_operand" "")
4914                        (match_operand:VI1_AVX2 2 "register_operand" "")))]
4915   "TARGET_SSE2
4916    && can_create_pseudo_p ()"
4917   "#"
4918   "&& 1"
4919   [(const_int 0)]
4920 {
4921   rtx t[6];
4922   int i;
4923   enum machine_mode mulmode = <sseunpackmode>mode;
4924
4925   for (i = 0; i < 6; ++i)
4926     t[i] = gen_reg_rtx (<MODE>mode);
4927
4928   /* Unpack data such that we've got a source byte in each low byte of
4929      each word.  We don't care what goes into the high byte of each word.
4930      Rather than trying to get zero in there, most convenient is to let
4931      it be a copy of the low byte.  */
4932   emit_insn (gen_<vec_avx2>_interleave_high<mode> (t[0], operands[1],
4933                                                    operands[1]));
4934   emit_insn (gen_<vec_avx2>_interleave_high<mode> (t[1], operands[2],
4935                                                    operands[2]));
4936   emit_insn (gen_<vec_avx2>_interleave_low<mode> (t[2], operands[1],
4937                                                   operands[1]));
4938   emit_insn (gen_<vec_avx2>_interleave_low<mode> (t[3], operands[2],
4939                                                   operands[2]));
4940
4941   /* Multiply words.  The end-of-line annotations here give a picture of what
4942      the output of that instruction looks like.  Dot means don't care; the
4943      letters are the bytes of the result with A being the most significant.  */
4944   emit_insn (gen_rtx_SET (VOIDmode, gen_lowpart (mulmode, t[4]),
4945                           gen_rtx_MULT (mulmode,        /* .A.B.C.D.E.F.G.H */
4946                                         gen_lowpart (mulmode, t[0]),
4947                                         gen_lowpart (mulmode, t[1]))));
4948   emit_insn (gen_rtx_SET (VOIDmode, gen_lowpart (mulmode, t[5]),
4949                           gen_rtx_MULT (mulmode,        /* .I.J.K.L.M.N.O.P */
4950                                         gen_lowpart (mulmode, t[2]),
4951                                         gen_lowpart (mulmode, t[3]))));
4952
4953   /* Extract the even bytes and merge them back together.  */
4954   ix86_expand_vec_extract_even_odd (operands[0], t[5], t[4], 0);
4955
4956   set_unique_reg_note (get_last_insn (), REG_EQUAL,
4957                        gen_rtx_MULT (<MODE>mode, operands[1], operands[2]));
4958   DONE;
4959 })
4960
4961 (define_expand "mul<mode>3"
4962   [(set (match_operand:VI2_AVX2 0 "register_operand" "")
4963         (mult:VI2_AVX2 (match_operand:VI2_AVX2 1 "nonimmediate_operand" "")
4964                        (match_operand:VI2_AVX2 2 "nonimmediate_operand" "")))]
4965   "TARGET_SSE2"
4966   "ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);")
4967
4968 (define_insn "*mul<mode>3"
4969   [(set (match_operand:VI2_AVX2 0 "register_operand" "=x,x")
4970         (mult:VI2_AVX2 (match_operand:VI2_AVX2 1 "nonimmediate_operand" "%0,x")
4971                        (match_operand:VI2_AVX2 2 "nonimmediate_operand" "xm,xm")))]
4972   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
4973   "@
4974    pmullw\t{%2, %0|%0, %2}
4975    vpmullw\t{%2, %1, %0|%0, %1, %2}"
4976   [(set_attr "isa" "noavx,avx")
4977    (set_attr "type" "sseimul")
4978    (set_attr "prefix_data16" "1,*")
4979    (set_attr "prefix" "orig,vex")
4980    (set_attr "mode" "<sseinsnmode>")])
4981
4982 (define_expand "<s>mul<mode>3_highpart"
4983   [(set (match_operand:VI2_AVX2 0 "register_operand" "")
4984         (truncate:VI2_AVX2
4985           (lshiftrt:<ssedoublemode>
4986             (mult:<ssedoublemode>
4987               (any_extend:<ssedoublemode>
4988                 (match_operand:VI2_AVX2 1 "nonimmediate_operand" ""))
4989               (any_extend:<ssedoublemode>
4990                 (match_operand:VI2_AVX2 2 "nonimmediate_operand" "")))
4991             (const_int 16))))]
4992   "TARGET_SSE2"
4993   "ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);")
4994
4995 (define_insn "*<s>mul<mode>3_highpart"
4996   [(set (match_operand:VI2_AVX2 0 "register_operand" "=x,x")
4997         (truncate:VI2_AVX2
4998           (lshiftrt:<ssedoublemode>
4999             (mult:<ssedoublemode>
5000               (any_extend:<ssedoublemode>
5001                 (match_operand:VI2_AVX2 1 "nonimmediate_operand" "%0,x"))
5002               (any_extend:<ssedoublemode>
5003                 (match_operand:VI2_AVX2 2 "nonimmediate_operand" "xm,xm")))
5004             (const_int 16))))]
5005   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
5006   "@
5007    pmulh<u>w\t{%2, %0|%0, %2}
5008    vpmulh<u>w\t{%2, %1, %0|%0, %1, %2}"
5009   [(set_attr "isa" "noavx,avx")
5010    (set_attr "type" "sseimul")
5011    (set_attr "prefix_data16" "1,*")
5012    (set_attr "prefix" "orig,vex")
5013    (set_attr "mode" "<sseinsnmode>")])
5014
5015 (define_expand "avx2_umulv4siv4di3"
5016   [(set (match_operand:V4DI 0 "register_operand" "")
5017         (mult:V4DI
5018           (zero_extend:V4DI
5019             (vec_select:V4SI
5020               (match_operand:V8SI 1 "nonimmediate_operand" "")
5021               (parallel [(const_int 0) (const_int 2)
5022                          (const_int 4) (const_int 6)])))
5023           (zero_extend:V4DI
5024             (vec_select:V4SI
5025               (match_operand:V8SI 2 "nonimmediate_operand" "")
5026               (parallel [(const_int 0) (const_int 2)
5027                          (const_int 4) (const_int 6)])))))]
5028   "TARGET_AVX2"
5029   "ix86_fixup_binary_operands_no_copy (MULT, V8SImode, operands);")
5030
5031 (define_insn "*avx_umulv4siv4di3"
5032   [(set (match_operand:V4DI 0 "register_operand" "=x")
5033         (mult:V4DI
5034           (zero_extend:V4DI
5035             (vec_select:V4SI
5036               (match_operand:V8SI 1 "nonimmediate_operand" "%x")
5037               (parallel [(const_int 0) (const_int 2)
5038                          (const_int 4) (const_int 6)])))
5039           (zero_extend:V4DI
5040             (vec_select:V4SI
5041               (match_operand:V8SI 2 "nonimmediate_operand" "xm")
5042               (parallel [(const_int 0) (const_int 2)
5043                          (const_int 4) (const_int 6)])))))]
5044   "TARGET_AVX2 && ix86_binary_operator_ok (MULT, V8SImode, operands)"
5045   "vpmuludq\t{%2, %1, %0|%0, %1, %2}"
5046   [(set_attr "type" "sseimul")
5047    (set_attr "prefix" "vex")
5048    (set_attr "mode" "OI")])
5049
5050 (define_expand "sse2_umulv2siv2di3"
5051   [(set (match_operand:V2DI 0 "register_operand" "")
5052         (mult:V2DI
5053           (zero_extend:V2DI
5054             (vec_select:V2SI
5055               (match_operand:V4SI 1 "nonimmediate_operand" "")
5056               (parallel [(const_int 0) (const_int 2)])))
5057           (zero_extend:V2DI
5058             (vec_select:V2SI
5059               (match_operand:V4SI 2 "nonimmediate_operand" "")
5060               (parallel [(const_int 0) (const_int 2)])))))]
5061   "TARGET_SSE2"
5062   "ix86_fixup_binary_operands_no_copy (MULT, V4SImode, operands);")
5063
5064 (define_insn "*sse2_umulv2siv2di3"
5065   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
5066         (mult:V2DI
5067           (zero_extend:V2DI
5068             (vec_select:V2SI
5069               (match_operand:V4SI 1 "nonimmediate_operand" "%0,x")
5070               (parallel [(const_int 0) (const_int 2)])))
5071           (zero_extend:V2DI
5072             (vec_select:V2SI
5073               (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm")
5074               (parallel [(const_int 0) (const_int 2)])))))]
5075   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V4SImode, operands)"
5076   "@
5077    pmuludq\t{%2, %0|%0, %2}
5078    vpmuludq\t{%2, %1, %0|%0, %1, %2}"
5079   [(set_attr "isa" "noavx,avx")
5080    (set_attr "type" "sseimul")
5081    (set_attr "prefix_data16" "1,*")
5082    (set_attr "prefix" "orig,vex")
5083    (set_attr "mode" "TI")])
5084
5085 (define_expand "avx2_mulv4siv4di3"
5086   [(set (match_operand:V4DI 0 "register_operand" "")
5087         (mult:V4DI
5088           (sign_extend:V4DI
5089             (vec_select:V4SI
5090               (match_operand:V8SI 1 "nonimmediate_operand" "")
5091               (parallel [(const_int 0) (const_int 2)
5092                          (const_int 4) (const_int 6)])))
5093           (sign_extend:V4DI
5094             (vec_select:V4SI
5095               (match_operand:V8SI 2 "nonimmediate_operand" "")
5096               (parallel [(const_int 0) (const_int 2)
5097                          (const_int 4) (const_int 6)])))))]
5098   "TARGET_AVX2"
5099   "ix86_fixup_binary_operands_no_copy (MULT, V8SImode, operands);")
5100
5101 (define_insn "*avx2_mulv4siv4di3"
5102   [(set (match_operand:V4DI 0 "register_operand" "=x")
5103         (mult:V4DI
5104           (sign_extend:V4DI
5105             (vec_select:V4SI
5106               (match_operand:V8SI 1 "nonimmediate_operand" "x")
5107               (parallel [(const_int 0) (const_int 2)
5108                          (const_int 4) (const_int 6)])))
5109           (sign_extend:V4DI
5110             (vec_select:V4SI
5111               (match_operand:V8SI 2 "nonimmediate_operand" "xm")
5112               (parallel [(const_int 0) (const_int 2)
5113                          (const_int 4) (const_int 6)])))))]
5114   "TARGET_AVX2 && ix86_binary_operator_ok (MULT, V8SImode, operands)"
5115   "vpmuldq\t{%2, %1, %0|%0, %1, %2}"
5116   [(set_attr "isa" "avx")
5117    (set_attr "type" "sseimul")
5118    (set_attr "prefix_extra" "1")
5119    (set_attr "prefix" "vex")
5120    (set_attr "mode" "OI")])
5121
5122 (define_expand "sse4_1_mulv2siv2di3"
5123   [(set (match_operand:V2DI 0 "register_operand" "")
5124         (mult:V2DI
5125           (sign_extend:V2DI
5126             (vec_select:V2SI
5127               (match_operand:V4SI 1 "nonimmediate_operand" "")
5128               (parallel [(const_int 0) (const_int 2)])))
5129           (sign_extend:V2DI
5130             (vec_select:V2SI
5131               (match_operand:V4SI 2 "nonimmediate_operand" "")
5132               (parallel [(const_int 0) (const_int 2)])))))]
5133   "TARGET_SSE4_1"
5134   "ix86_fixup_binary_operands_no_copy (MULT, V4SImode, operands);")
5135
5136 (define_insn "*sse4_1_mulv2siv2di3"
5137   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
5138         (mult:V2DI
5139           (sign_extend:V2DI
5140             (vec_select:V2SI
5141               (match_operand:V4SI 1 "nonimmediate_operand" "%0,x")
5142               (parallel [(const_int 0) (const_int 2)])))
5143           (sign_extend:V2DI
5144             (vec_select:V2SI
5145               (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm")
5146               (parallel [(const_int 0) (const_int 2)])))))]
5147   "TARGET_SSE4_1 && ix86_binary_operator_ok (MULT, V4SImode, operands)"
5148   "@
5149    pmuldq\t{%2, %0|%0, %2}
5150    vpmuldq\t{%2, %1, %0|%0, %1, %2}"
5151   [(set_attr "isa" "noavx,avx")
5152    (set_attr "type" "sseimul")
5153    (set_attr "prefix_data16" "1,*")
5154    (set_attr "prefix_extra" "1")
5155    (set_attr "prefix" "orig,vex")
5156    (set_attr "mode" "TI")])
5157
5158 (define_expand "avx2_pmaddwd"
5159   [(set (match_operand:V8SI 0 "register_operand" "")
5160         (plus:V8SI
5161           (mult:V8SI
5162             (sign_extend:V8SI
5163               (vec_select:V8HI
5164                 (match_operand:V16HI 1 "nonimmediate_operand" "")
5165                 (parallel [(const_int 0)
5166                            (const_int 2)
5167                            (const_int 4)
5168                            (const_int 6)
5169                            (const_int 8)
5170                            (const_int 10)
5171                            (const_int 12)
5172                            (const_int 14)])))
5173             (sign_extend:V8SI
5174               (vec_select:V8HI
5175                 (match_operand:V16HI 2 "nonimmediate_operand" "")
5176                 (parallel [(const_int 0)
5177                            (const_int 2)
5178                            (const_int 4)
5179                            (const_int 6)
5180                            (const_int 8)
5181                            (const_int 10)
5182                            (const_int 12)
5183                            (const_int 14)]))))
5184           (mult:V8SI
5185             (sign_extend:V8SI
5186               (vec_select:V8HI (match_dup 1)
5187                 (parallel [(const_int 1)
5188                            (const_int 3)
5189                            (const_int 5)
5190                            (const_int 7)
5191                            (const_int 9)
5192                            (const_int 11)
5193                            (const_int 13)
5194                            (const_int 15)])))
5195             (sign_extend:V8SI
5196               (vec_select:V8HI (match_dup 2)
5197                 (parallel [(const_int 1)
5198                            (const_int 3)
5199                            (const_int 5)
5200                            (const_int 7)
5201                            (const_int 9)
5202                            (const_int 11)
5203                            (const_int 13)
5204                            (const_int 15)]))))))]
5205   "TARGET_AVX2"
5206   "ix86_fixup_binary_operands_no_copy (MULT, V16HImode, operands);")
5207
5208 (define_expand "sse2_pmaddwd"
5209   [(set (match_operand:V4SI 0 "register_operand" "")
5210         (plus:V4SI
5211           (mult:V4SI
5212             (sign_extend:V4SI
5213               (vec_select:V4HI
5214                 (match_operand:V8HI 1 "nonimmediate_operand" "")
5215                 (parallel [(const_int 0)
5216                            (const_int 2)
5217                            (const_int 4)
5218                            (const_int 6)])))
5219             (sign_extend:V4SI
5220               (vec_select:V4HI
5221                 (match_operand:V8HI 2 "nonimmediate_operand" "")
5222                 (parallel [(const_int 0)
5223                            (const_int 2)
5224                            (const_int 4)
5225                            (const_int 6)]))))
5226           (mult:V4SI
5227             (sign_extend:V4SI
5228               (vec_select:V4HI (match_dup 1)
5229                 (parallel [(const_int 1)
5230                            (const_int 3)
5231                            (const_int 5)
5232                            (const_int 7)])))
5233             (sign_extend:V4SI
5234               (vec_select:V4HI (match_dup 2)
5235                 (parallel [(const_int 1)
5236                            (const_int 3)
5237                            (const_int 5)
5238                            (const_int 7)]))))))]
5239   "TARGET_SSE2"
5240   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
5241
5242 (define_insn "*avx2_pmaddwd"
5243   [(set (match_operand:V8SI 0 "register_operand" "=x")
5244         (plus:V8SI
5245           (mult:V8SI
5246             (sign_extend:V8SI
5247               (vec_select:V8HI
5248                 (match_operand:V16HI 1 "nonimmediate_operand" "%x")
5249                 (parallel [(const_int 0)
5250                            (const_int 2)
5251                            (const_int 4)
5252                            (const_int 6)
5253                            (const_int 8)
5254                            (const_int 10)
5255                            (const_int 12)
5256                            (const_int 14)])))
5257             (sign_extend:V8SI
5258               (vec_select:V8HI
5259                 (match_operand:V16HI 2 "nonimmediate_operand" "xm")
5260                 (parallel [(const_int 0)
5261                            (const_int 2)
5262                            (const_int 4)
5263                            (const_int 6)
5264                            (const_int 8)
5265                            (const_int 10)
5266                            (const_int 12)
5267                            (const_int 14)]))))
5268           (mult:V8SI
5269             (sign_extend:V8SI
5270               (vec_select:V8HI (match_dup 1)
5271                 (parallel [(const_int 1)
5272                            (const_int 3)
5273                            (const_int 5)
5274                            (const_int 7)
5275                            (const_int 9)
5276                            (const_int 11)
5277                            (const_int 13)
5278                            (const_int 15)])))
5279             (sign_extend:V8SI
5280               (vec_select:V8HI (match_dup 2)
5281                 (parallel [(const_int 1)
5282                            (const_int 3)
5283                            (const_int 5)
5284                            (const_int 7)
5285                            (const_int 9)
5286                            (const_int 11)
5287                            (const_int 13)
5288                            (const_int 15)]))))))]
5289   "TARGET_AVX2 && ix86_binary_operator_ok (MULT, V16HImode, operands)"
5290   "vpmaddwd\t{%2, %1, %0|%0, %1, %2}"
5291   [(set_attr "type" "sseiadd")
5292    (set_attr "prefix" "vex")
5293    (set_attr "mode" "OI")])
5294
5295 (define_insn "*sse2_pmaddwd"
5296   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
5297         (plus:V4SI
5298           (mult:V4SI
5299             (sign_extend:V4SI
5300               (vec_select:V4HI
5301                 (match_operand:V8HI 1 "nonimmediate_operand" "%0,x")
5302                 (parallel [(const_int 0)
5303                            (const_int 2)
5304                            (const_int 4)
5305                            (const_int 6)])))
5306             (sign_extend:V4SI
5307               (vec_select:V4HI
5308                 (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
5309                 (parallel [(const_int 0)
5310                            (const_int 2)
5311                            (const_int 4)
5312                            (const_int 6)]))))
5313           (mult:V4SI
5314             (sign_extend:V4SI
5315               (vec_select:V4HI (match_dup 1)
5316                 (parallel [(const_int 1)
5317                            (const_int 3)
5318                            (const_int 5)
5319                            (const_int 7)])))
5320             (sign_extend:V4SI
5321               (vec_select:V4HI (match_dup 2)
5322                 (parallel [(const_int 1)
5323                            (const_int 3)
5324                            (const_int 5)
5325                            (const_int 7)]))))))]
5326   "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
5327   "@
5328    pmaddwd\t{%2, %0|%0, %2}
5329    vpmaddwd\t{%2, %1, %0|%0, %1, %2}"
5330   [(set_attr "isa" "noavx,avx")
5331    (set_attr "type" "sseiadd")
5332    (set_attr "atom_unit" "simul")
5333    (set_attr "prefix_data16" "1,*")
5334    (set_attr "prefix" "orig,vex")
5335    (set_attr "mode" "TI")])
5336
5337 (define_expand "mul<mode>3"
5338   [(set (match_operand:VI4_AVX2 0 "register_operand" "")
5339         (mult:VI4_AVX2 (match_operand:VI4_AVX2 1 "register_operand" "")
5340                        (match_operand:VI4_AVX2 2 "register_operand" "")))]
5341   "TARGET_SSE2"
5342 {
5343   if (TARGET_SSE4_1 || TARGET_AVX)
5344     ix86_fixup_binary_operands_no_copy (MULT, <MODE>mode, operands);
5345 })
5346
5347 (define_insn "*<sse4_1_avx2>_mul<mode>3"
5348   [(set (match_operand:VI4_AVX2 0 "register_operand" "=x,x")
5349         (mult:VI4_AVX2 (match_operand:VI4_AVX2 1 "nonimmediate_operand" "%0,x")
5350                        (match_operand:VI4_AVX2 2 "nonimmediate_operand" "xm,xm")))]
5351   "TARGET_SSE4_1 && ix86_binary_operator_ok (MULT, <MODE>mode, operands)"
5352   "@
5353    pmulld\t{%2, %0|%0, %2}
5354    vpmulld\t{%2, %1, %0|%0, %1, %2}"
5355   [(set_attr "isa" "noavx,avx")
5356    (set_attr "type" "sseimul")
5357    (set_attr "prefix_extra" "1")
5358    (set_attr "prefix" "orig,vex")
5359    (set_attr "mode" "<sseinsnmode>")])
5360
5361 (define_insn_and_split "*sse2_mulv4si3"
5362   [(set (match_operand:V4SI 0 "register_operand" "")
5363         (mult:V4SI (match_operand:V4SI 1 "register_operand" "")
5364                    (match_operand:V4SI 2 "register_operand" "")))]
5365   "TARGET_SSE2 && !TARGET_SSE4_1 && !TARGET_AVX
5366    && can_create_pseudo_p ()"
5367   "#"
5368   "&& 1"
5369   [(const_int 0)]
5370 {
5371   rtx t1, t2, t3, t4, t5, t6, thirtytwo;
5372   rtx op0, op1, op2;
5373
5374   op0 = operands[0];
5375   op1 = operands[1];
5376   op2 = operands[2];
5377   t1 = gen_reg_rtx (V4SImode);
5378   t2 = gen_reg_rtx (V4SImode);
5379   t3 = gen_reg_rtx (V4SImode);
5380   t4 = gen_reg_rtx (V4SImode);
5381   t5 = gen_reg_rtx (V4SImode);
5382   t6 = gen_reg_rtx (V4SImode);
5383   thirtytwo = GEN_INT (32);
5384
5385   /* Multiply elements 2 and 0.  */
5386   emit_insn (gen_sse2_umulv2siv2di3 (gen_lowpart (V2DImode, t1),
5387                                      op1, op2));
5388
5389   /* Shift both input vectors down one element, so that elements 3
5390      and 1 are now in the slots for elements 2 and 0.  For K8, at
5391      least, this is faster than using a shuffle.  */
5392   emit_insn (gen_sse2_lshrv1ti3 (gen_lowpart (V1TImode, t2),
5393                                  gen_lowpart (V1TImode, op1),
5394                                  thirtytwo));
5395   emit_insn (gen_sse2_lshrv1ti3 (gen_lowpart (V1TImode, t3),
5396                                  gen_lowpart (V1TImode, op2),
5397                                  thirtytwo));
5398   /* Multiply elements 3 and 1.  */
5399   emit_insn (gen_sse2_umulv2siv2di3 (gen_lowpart (V2DImode, t4),
5400                                      t2, t3));
5401
5402   /* Move the results in element 2 down to element 1; we don't care
5403      what goes in elements 2 and 3.  */
5404   emit_insn (gen_sse2_pshufd_1 (t5, t1, const0_rtx, const2_rtx,
5405                                 const0_rtx, const0_rtx));
5406   emit_insn (gen_sse2_pshufd_1 (t6, t4, const0_rtx, const2_rtx,
5407                                 const0_rtx, const0_rtx));
5408
5409   /* Merge the parts back together.  */
5410   emit_insn (gen_vec_interleave_lowv4si (op0, t5, t6));
5411
5412   set_unique_reg_note (get_last_insn (), REG_EQUAL,
5413                        gen_rtx_MULT (V4SImode, operands[1], operands[2]));
5414   DONE;
5415 })
5416
5417 (define_insn_and_split "mul<mode>3"
5418   [(set (match_operand:VI8_AVX2 0 "register_operand" "")
5419         (mult:VI8_AVX2 (match_operand:VI8_AVX2 1 "register_operand" "")
5420                        (match_operand:VI8_AVX2 2 "register_operand" "")))]
5421   "TARGET_SSE2
5422    && can_create_pseudo_p ()"
5423   "#"
5424   "&& 1"
5425   [(const_int 0)]
5426 {
5427   rtx t1, t2, t3, t4, t5, t6, thirtytwo;
5428   rtx op0, op1, op2;
5429
5430   op0 = operands[0];
5431   op1 = operands[1];
5432   op2 = operands[2];
5433
5434   if (TARGET_XOP && <MODE>mode == V2DImode)
5435     {
5436       /* op1: A,B,C,D, op2: E,F,G,H */
5437       op1 = gen_lowpart (V4SImode, op1);
5438       op2 = gen_lowpart (V4SImode, op2);
5439
5440       t1 = gen_reg_rtx (V4SImode);
5441       t2 = gen_reg_rtx (V4SImode);
5442       t3 = gen_reg_rtx (V2DImode);
5443       t4 = gen_reg_rtx (V2DImode);
5444
5445       /* t1: B,A,D,C */
5446       emit_insn (gen_sse2_pshufd_1 (t1, op1,
5447                                     GEN_INT (1),
5448                                     GEN_INT (0),
5449                                     GEN_INT (3),
5450                                     GEN_INT (2)));
5451
5452       /* t2: (B*E),(A*F),(D*G),(C*H) */
5453       emit_insn (gen_mulv4si3 (t2, t1, op2));
5454
5455       /* t4: (B*E)+(A*F), (D*G)+(C*H) */
5456       emit_insn (gen_xop_phadddq (t3, t2));
5457
5458       /* t5: ((B*E)+(A*F))<<32, ((D*G)+(C*H))<<32 */
5459       emit_insn (gen_ashlv2di3 (t4, t3, GEN_INT (32)));
5460
5461       /* op0: (((B*E)+(A*F))<<32)+(B*F), (((D*G)+(C*H))<<32)+(D*H) */
5462       emit_insn (gen_xop_pmacsdql (op0, op1, op2, t4));
5463     }
5464   else
5465     {
5466       t1 = gen_reg_rtx (<MODE>mode);
5467       t2 = gen_reg_rtx (<MODE>mode);
5468       t3 = gen_reg_rtx (<MODE>mode);
5469       t4 = gen_reg_rtx (<MODE>mode);
5470       t5 = gen_reg_rtx (<MODE>mode);
5471       t6 = gen_reg_rtx (<MODE>mode);
5472       thirtytwo = GEN_INT (32);
5473
5474       /* Multiply low parts.  */
5475       emit_insn (gen_<sse2_avx2>_umulv<ssescalarnum>si<mode>3
5476                   (t1, gen_lowpart (<ssepackmode>mode, op1),
5477                    gen_lowpart (<ssepackmode>mode, op2)));
5478
5479       /* Shift input vectors right 32 bits so we can multiply high parts.  */
5480       emit_insn (gen_lshr<mode>3 (t2, op1, thirtytwo));
5481       emit_insn (gen_lshr<mode>3 (t3, op2, thirtytwo));
5482
5483       /* Multiply high parts by low parts.  */
5484       emit_insn (gen_<sse2_avx2>_umulv<ssescalarnum>si<mode>3
5485                   (t4, gen_lowpart (<ssepackmode>mode, op1),
5486                    gen_lowpart (<ssepackmode>mode, t3)));
5487       emit_insn (gen_<sse2_avx2>_umulv<ssescalarnum>si<mode>3
5488                   (t5, gen_lowpart (<ssepackmode>mode, op2),
5489                    gen_lowpart (<ssepackmode>mode, t2)));
5490
5491       /* Shift them back.  */
5492       emit_insn (gen_ashl<mode>3 (t4, t4, thirtytwo));
5493       emit_insn (gen_ashl<mode>3 (t5, t5, thirtytwo));
5494
5495       /* Add the three parts together.  */
5496       emit_insn (gen_add<mode>3 (t6, t1, t4));
5497       emit_insn (gen_add<mode>3 (op0, t6, t5));
5498     }
5499
5500   set_unique_reg_note (get_last_insn (), REG_EQUAL,
5501                        gen_rtx_MULT (<MODE>mode, operands[1], operands[2]));
5502   DONE;
5503 })
5504
5505 (define_expand "vec_widen_<s>mult_hi_<mode>"
5506   [(match_operand:<sseunpackmode> 0 "register_operand" "")
5507    (any_extend:<sseunpackmode>
5508      (match_operand:VI2_AVX2 1 "register_operand" ""))
5509    (match_operand:VI2_AVX2 2 "register_operand" "")]
5510   "TARGET_SSE2"
5511 {
5512   rtx op1, op2, t1, t2, dest;
5513
5514   op1 = operands[1];
5515   op2 = operands[2];
5516   t1 = gen_reg_rtx (<MODE>mode);
5517   t2 = gen_reg_rtx (<MODE>mode);
5518   dest = gen_lowpart (<MODE>mode, operands[0]);
5519
5520   emit_insn (gen_mul<mode>3 (t1, op1, op2));
5521   emit_insn (gen_<s>mul<mode>3_highpart (t2, op1, op2));
5522   emit_insn (gen_vec_interleave_high<mode> (dest, t1, t2));
5523   DONE;
5524 })
5525
5526 (define_expand "vec_widen_<s>mult_lo_<mode>"
5527   [(match_operand:<sseunpackmode> 0 "register_operand" "")
5528    (any_extend:<sseunpackmode>
5529      (match_operand:VI2_AVX2 1 "register_operand" ""))
5530    (match_operand:VI2_AVX2 2 "register_operand" "")]
5531   "TARGET_SSE2"
5532 {
5533   rtx op1, op2, t1, t2, dest;
5534
5535   op1 = operands[1];
5536   op2 = operands[2];
5537   t1 = gen_reg_rtx (<MODE>mode);
5538   t2 = gen_reg_rtx (<MODE>mode);
5539   dest = gen_lowpart (<MODE>mode, operands[0]);
5540
5541   emit_insn (gen_mul<mode>3 (t1, op1, op2));
5542   emit_insn (gen_<s>mul<mode>3_highpart (t2, op1, op2));
5543   emit_insn (gen_vec_interleave_low<mode> (dest, t1, t2));
5544   DONE;
5545 })
5546
5547 (define_expand "vec_widen_<s>mult_hi_v8si"
5548   [(match_operand:V4DI 0 "register_operand" "")
5549    (any_extend:V4DI (match_operand:V8SI 1 "nonimmediate_operand" ""))
5550    (match_operand:V8SI 2 "nonimmediate_operand" "")]
5551   "TARGET_AVX2"
5552 {
5553   rtx t1, t2, t3, t4;
5554
5555   t1 = gen_reg_rtx (V4DImode);
5556   t2 = gen_reg_rtx (V4DImode);
5557   t3 = gen_reg_rtx (V8SImode);
5558   t4 = gen_reg_rtx (V8SImode);
5559   emit_insn (gen_avx2_permv4di_1 (t1, gen_lowpart (V4DImode, operands[1]),
5560                                   const0_rtx, const2_rtx,
5561                                   const1_rtx, GEN_INT (3)));
5562   emit_insn (gen_avx2_permv4di_1 (t2, gen_lowpart (V4DImode, operands[2]),
5563                                   const0_rtx, const2_rtx,
5564                                   const1_rtx, GEN_INT (3)));
5565   emit_insn (gen_avx2_pshufdv3 (t3, gen_lowpart (V8SImode, t1),
5566                                 GEN_INT (2 + (2 << 2) + (3 << 4) + (3 << 6))));
5567   emit_insn (gen_avx2_pshufdv3 (t4, gen_lowpart (V8SImode, t2),
5568                                 GEN_INT (2 + (2 << 2) + (3 << 4) + (3 << 6))));
5569   emit_insn (gen_avx2_<u>mulv4siv4di3 (operands[0], t3, t4));
5570   DONE;
5571 })
5572
5573 (define_expand "vec_widen_<s>mult_lo_v8si"
5574   [(match_operand:V4DI 0 "register_operand" "")
5575    (any_extend:V4DI (match_operand:V8SI 1 "nonimmediate_operand" ""))
5576    (match_operand:V8SI 2 "nonimmediate_operand" "")]
5577   "TARGET_AVX2"
5578 {
5579   rtx t1, t2, t3, t4;
5580
5581   t1 = gen_reg_rtx (V4DImode);
5582   t2 = gen_reg_rtx (V4DImode);
5583   t3 = gen_reg_rtx (V8SImode);
5584   t4 = gen_reg_rtx (V8SImode);
5585   emit_insn (gen_avx2_permv4di_1 (t1, gen_lowpart (V4DImode, operands[1]),
5586                                   const0_rtx, const2_rtx,
5587                                   const1_rtx, GEN_INT (3)));
5588   emit_insn (gen_avx2_permv4di_1 (t2,  gen_lowpart (V4DImode, operands[2]),
5589                                   const0_rtx, const2_rtx,
5590                                   const1_rtx, GEN_INT (3)));
5591   emit_insn (gen_avx2_pshufdv3 (t3, gen_lowpart (V8SImode, t1),
5592                                 GEN_INT (0 + (0 << 2) + (1 << 4) + (1 << 6))));
5593   emit_insn (gen_avx2_pshufdv3 (t4, gen_lowpart (V8SImode, t2),
5594                                 GEN_INT (0 + (0 << 2) + (1 << 4) + (1 << 6))));
5595   emit_insn (gen_avx2_<u>mulv4siv4di3 (operands[0], t3, t4));
5596   DONE;
5597 })
5598
5599 (define_expand "vec_widen_smult_hi_v4si"
5600   [(match_operand:V2DI 0 "register_operand" "")
5601    (match_operand:V4SI 1 "register_operand" "")
5602    (match_operand:V4SI 2 "register_operand" "")]
5603   "TARGET_SSE4_1"
5604 {
5605   rtx op1, op2, t1, t2;
5606
5607   op1 = operands[1];
5608   op2 = operands[2];
5609   t1 = gen_reg_rtx (V4SImode);
5610   t2 = gen_reg_rtx (V4SImode);
5611
5612   if (TARGET_XOP)
5613     {
5614       emit_insn (gen_sse2_pshufd_1 (t1, op1, GEN_INT (0), GEN_INT (2),
5615                                     GEN_INT (1), GEN_INT (3)));
5616       emit_insn (gen_sse2_pshufd_1 (t2, op2, GEN_INT (0), GEN_INT (2),
5617                                     GEN_INT (1), GEN_INT (3)));
5618       emit_insn (gen_xop_mulv2div2di3_high (operands[0], t1, t2));
5619       DONE;
5620     }
5621
5622   emit_insn (gen_vec_interleave_highv4si (t1, op1, op1));
5623   emit_insn (gen_vec_interleave_highv4si (t2, op2, op2));
5624   emit_insn (gen_sse4_1_mulv2siv2di3 (operands[0], t1, t2));
5625   DONE;
5626 })
5627
5628 (define_expand "vec_widen_smult_lo_v4si"
5629   [(match_operand:V2DI 0 "register_operand" "")
5630    (match_operand:V4SI 1 "register_operand" "")
5631    (match_operand:V4SI 2 "register_operand" "")]
5632   "TARGET_SSE4_1"
5633 {
5634   rtx op1, op2, t1, t2;
5635
5636   op1 = operands[1];
5637   op2 = operands[2];
5638   t1 = gen_reg_rtx (V4SImode);
5639   t2 = gen_reg_rtx (V4SImode);
5640
5641   if (TARGET_XOP)
5642     {
5643       emit_insn (gen_sse2_pshufd_1 (t1, op1, GEN_INT (0), GEN_INT (2),
5644                                     GEN_INT (1), GEN_INT (3)));
5645       emit_insn (gen_sse2_pshufd_1 (t2, op2, GEN_INT (0), GEN_INT (2),
5646                                     GEN_INT (1), GEN_INT (3)));
5647       emit_insn (gen_xop_mulv2div2di3_low (operands[0], t1, t2));
5648       DONE;
5649     }
5650
5651   emit_insn (gen_vec_interleave_lowv4si (t1, op1, op1));
5652   emit_insn (gen_vec_interleave_lowv4si (t2, op2, op2));
5653   emit_insn (gen_sse4_1_mulv2siv2di3 (operands[0], t1, t2));
5654   DONE;
5655 })
5656
5657 (define_expand "vec_widen_umult_hi_v4si"
5658   [(match_operand:V2DI 0 "register_operand" "")
5659    (match_operand:V4SI 1 "register_operand" "")
5660    (match_operand:V4SI 2 "register_operand" "")]
5661   "TARGET_SSE2"
5662 {
5663   rtx op1, op2, t1, t2;
5664
5665   op1 = operands[1];
5666   op2 = operands[2];
5667   t1 = gen_reg_rtx (V4SImode);
5668   t2 = gen_reg_rtx (V4SImode);
5669
5670   emit_insn (gen_vec_interleave_highv4si (t1, op1, op1));
5671   emit_insn (gen_vec_interleave_highv4si (t2, op2, op2));
5672   emit_insn (gen_sse2_umulv2siv2di3 (operands[0], t1, t2));
5673   DONE;
5674 })
5675
5676 (define_expand "vec_widen_umult_lo_v4si"
5677   [(match_operand:V2DI 0 "register_operand" "")
5678    (match_operand:V4SI 1 "register_operand" "")
5679    (match_operand:V4SI 2 "register_operand" "")]
5680   "TARGET_SSE2"
5681 {
5682   rtx op1, op2, t1, t2;
5683
5684   op1 = operands[1];
5685   op2 = operands[2];
5686   t1 = gen_reg_rtx (V4SImode);
5687   t2 = gen_reg_rtx (V4SImode);
5688
5689   emit_insn (gen_vec_interleave_lowv4si (t1, op1, op1));
5690   emit_insn (gen_vec_interleave_lowv4si (t2, op2, op2));
5691   emit_insn (gen_sse2_umulv2siv2di3 (operands[0], t1, t2));
5692   DONE;
5693 })
5694
5695 (define_expand "sdot_prod<mode>"
5696   [(match_operand:<sseunpackmode> 0 "register_operand" "")
5697    (match_operand:VI2_AVX2 1 "register_operand" "")
5698    (match_operand:VI2_AVX2 2 "register_operand" "")
5699    (match_operand:<sseunpackmode> 3 "register_operand" "")]
5700   "TARGET_SSE2"
5701 {
5702   rtx t = gen_reg_rtx (<sseunpackmode>mode);
5703   emit_insn (gen_<sse2_avx2>_pmaddwd (t, operands[1], operands[2]));
5704   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
5705                           gen_rtx_PLUS (<sseunpackmode>mode,
5706                                         operands[3], t)));
5707   DONE;
5708 })
5709
5710 (define_code_attr sse2_sse4_1
5711    [(zero_extend "sse2") (sign_extend "sse4_1")])
5712
5713 (define_expand "<s>dot_prodv4si"
5714   [(match_operand:V2DI 0 "register_operand" "")
5715    (any_extend:V2DI (match_operand:V4SI 1 "register_operand" ""))
5716    (match_operand:V4SI 2 "register_operand" "")
5717    (match_operand:V2DI 3 "register_operand" "")]
5718   "<CODE> == ZERO_EXTEND ? TARGET_SSE2 : TARGET_SSE4_1"
5719 {
5720   rtx t1, t2, t3, t4;
5721
5722   t1 = gen_reg_rtx (V2DImode);
5723   emit_insn (gen_<sse2_sse4_1>_<u>mulv2siv2di3 (t1, operands[1], operands[2]));
5724   emit_insn (gen_addv2di3 (t1, t1, operands[3]));
5725
5726   t2 = gen_reg_rtx (V4SImode);
5727   t3 = gen_reg_rtx (V4SImode);
5728   emit_insn (gen_sse2_lshrv1ti3 (gen_lowpart (V1TImode, t2),
5729                                  gen_lowpart (V1TImode, operands[1]),
5730                                  GEN_INT (32)));
5731   emit_insn (gen_sse2_lshrv1ti3 (gen_lowpart (V1TImode, t3),
5732                                  gen_lowpart (V1TImode, operands[2]),
5733                                  GEN_INT (32)));
5734
5735   t4 = gen_reg_rtx (V2DImode);
5736   emit_insn (gen_<sse2_sse4_1>_<u>mulv2siv2di3 (t4, t2, t3));
5737
5738   emit_insn (gen_addv2di3 (operands[0], t1, t4));
5739   DONE;
5740 })
5741
5742 (define_expand "<s>dot_prodv8si"
5743   [(match_operand:V4DI 0 "register_operand" "")
5744    (any_extend:V4DI (match_operand:V8SI 1 "register_operand" ""))
5745    (match_operand:V8SI 2 "register_operand" "")
5746    (match_operand:V4DI 3 "register_operand" "")]
5747   "TARGET_AVX2"
5748 {
5749   rtx t1, t2, t3, t4;
5750
5751   t1 = gen_reg_rtx (V4DImode);
5752   emit_insn (gen_avx2_<u>mulv4siv4di3 (t1, operands[1], operands[2]));
5753   emit_insn (gen_addv4di3 (t1, t1, operands[3]));
5754
5755   t2 = gen_reg_rtx (V8SImode);
5756   t3 = gen_reg_rtx (V8SImode);
5757   emit_insn (gen_avx2_lshrv2ti3 (gen_lowpart (V2TImode, t2),
5758                                  gen_lowpart (V2TImode, operands[1]),
5759                                  GEN_INT (32)));
5760   emit_insn (gen_avx2_lshrv2ti3 (gen_lowpart (V2TImode, t3),
5761                                  gen_lowpart (V2TImode, operands[2]),
5762                                  GEN_INT (32)));
5763
5764   t4 = gen_reg_rtx (V4DImode);
5765   emit_insn (gen_avx2_<u>mulv4siv4di3 (t4, t2, t3));
5766
5767   emit_insn (gen_addv4di3 (operands[0], t1, t4));
5768   DONE;
5769 })
5770
5771 (define_insn "ashr<mode>3"
5772   [(set (match_operand:VI24_AVX2 0 "register_operand" "=x,x")
5773         (ashiftrt:VI24_AVX2
5774           (match_operand:VI24_AVX2 1 "register_operand" "0,x")
5775           (match_operand:SI 2 "nonmemory_operand" "xN,xN")))]
5776   "TARGET_SSE2"
5777   "@
5778    psra<ssemodesuffix>\t{%2, %0|%0, %2}
5779    vpsra<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
5780   [(set_attr "isa" "noavx,avx")
5781    (set_attr "type" "sseishft")
5782    (set (attr "length_immediate")
5783      (if_then_else (match_operand 2 "const_int_operand" "")
5784        (const_string "1")
5785        (const_string "0")))
5786    (set_attr "prefix_data16" "1,*")
5787    (set_attr "prefix" "orig,vex")
5788    (set_attr "mode" "<sseinsnmode>")])
5789
5790 (define_insn "<shift_insn><mode>3"
5791   [(set (match_operand:VI248_AVX2 0 "register_operand" "=x,x")
5792         (any_lshift:VI248_AVX2
5793           (match_operand:VI248_AVX2 1 "register_operand" "0,x")
5794           (match_operand:SI 2 "nonmemory_operand" "xN,xN")))]
5795   "TARGET_SSE2"
5796   "@
5797    p<vshift><ssemodesuffix>\t{%2, %0|%0, %2}
5798    vp<vshift><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
5799   [(set_attr "isa" "noavx,avx")
5800    (set_attr "type" "sseishft")
5801    (set (attr "length_immediate")
5802      (if_then_else (match_operand 2 "const_int_operand" "")
5803        (const_string "1")
5804        (const_string "0")))
5805    (set_attr "prefix_data16" "1,*")
5806    (set_attr "prefix" "orig,vex")
5807    (set_attr "mode" "<sseinsnmode>")])
5808
5809 (define_expand "vec_shl_<mode>"
5810   [(set (match_operand:VI_128 0 "register_operand" "")
5811         (ashift:V1TI
5812          (match_operand:VI_128 1 "register_operand" "")
5813          (match_operand:SI 2 "const_0_to_255_mul_8_operand" "")))]
5814   "TARGET_SSE2"
5815 {
5816   operands[0] = gen_lowpart (V1TImode, operands[0]);
5817   operands[1] = gen_lowpart (V1TImode, operands[1]);
5818 })
5819
5820 (define_insn "<sse2_avx2>_ashl<mode>3"
5821   [(set (match_operand:VIMAX_AVX2 0 "register_operand" "=x,x")
5822         (ashift:VIMAX_AVX2
5823          (match_operand:VIMAX_AVX2 1 "register_operand" "0,x")
5824          (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n,n")))]
5825   "TARGET_SSE2"
5826 {
5827   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
5828
5829   switch (which_alternative)
5830     {
5831     case 0:
5832       return "pslldq\t{%2, %0|%0, %2}";
5833     case 1:
5834       return "vpslldq\t{%2, %1, %0|%0, %1, %2}";
5835     default:
5836       gcc_unreachable ();
5837     }
5838 }
5839   [(set_attr "isa" "noavx,avx")
5840    (set_attr "type" "sseishft")
5841    (set_attr "length_immediate" "1")
5842    (set_attr "prefix_data16" "1,*")
5843    (set_attr "prefix" "orig,vex")
5844    (set_attr "mode" "<sseinsnmode>")])
5845
5846 (define_expand "vec_shr_<mode>"
5847   [(set (match_operand:VI_128 0 "register_operand" "")
5848         (lshiftrt:V1TI
5849          (match_operand:VI_128 1 "register_operand" "")
5850          (match_operand:SI 2 "const_0_to_255_mul_8_operand" "")))]
5851   "TARGET_SSE2"
5852 {
5853   operands[0] = gen_lowpart (V1TImode, operands[0]);
5854   operands[1] = gen_lowpart (V1TImode, operands[1]);
5855 })
5856
5857 (define_insn "<sse2_avx2>_lshr<mode>3"
5858   [(set (match_operand:VIMAX_AVX2 0 "register_operand" "=x,x")
5859         (lshiftrt:VIMAX_AVX2
5860          (match_operand:VIMAX_AVX2 1 "register_operand" "0,x")
5861          (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n,n")))]
5862   "TARGET_SSE2"
5863 {
5864   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
5865
5866   switch (which_alternative)
5867     {
5868     case 0:
5869       return "psrldq\t{%2, %0|%0, %2}";
5870     case 1:
5871       return "vpsrldq\t{%2, %1, %0|%0, %1, %2}";
5872     default:
5873       gcc_unreachable ();
5874     }
5875 }
5876   [(set_attr "isa" "noavx,avx")
5877    (set_attr "type" "sseishft")
5878    (set_attr "length_immediate" "1")
5879    (set_attr "atom_unit" "sishuf")
5880    (set_attr "prefix_data16" "1,*")
5881    (set_attr "prefix" "orig,vex")
5882    (set_attr "mode" "<sseinsnmode>")])
5883
5884
5885 (define_expand "<code><mode>3"
5886   [(set (match_operand:VI124_256 0 "register_operand" "")
5887         (maxmin:VI124_256
5888           (match_operand:VI124_256 1 "nonimmediate_operand" "")
5889           (match_operand:VI124_256 2 "nonimmediate_operand" "")))]
5890   "TARGET_AVX2"
5891   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
5892
5893 (define_insn "*avx2_<code><mode>3"
5894   [(set (match_operand:VI124_256 0 "register_operand" "=x")
5895         (maxmin:VI124_256
5896           (match_operand:VI124_256 1 "nonimmediate_operand" "%x")
5897           (match_operand:VI124_256 2 "nonimmediate_operand" "xm")))]
5898   "TARGET_AVX2 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5899   "vp<maxmin_int><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
5900   [(set_attr "type" "sseiadd")
5901    (set_attr "prefix_extra" "1")
5902    (set_attr "prefix" "vex")
5903    (set_attr "mode" "OI")])
5904
5905 (define_expand "<code><mode>3"
5906   [(set (match_operand:VI8_AVX2 0 "register_operand" "")
5907         (maxmin:VI8_AVX2
5908           (match_operand:VI8_AVX2 1 "register_operand" "")
5909           (match_operand:VI8_AVX2 2 "register_operand" "")))]
5910   "TARGET_SSE4_2"
5911 {
5912   enum rtx_code code;
5913   rtx xops[6];
5914   bool ok;
5915
5916   xops[0] = operands[0];
5917
5918   if (<CODE> == SMAX || <CODE> == UMAX)
5919     {
5920       xops[1] = operands[1];
5921       xops[2] = operands[2];
5922     }
5923   else
5924     {
5925       xops[1] = operands[2];
5926       xops[2] = operands[1];
5927     }
5928
5929   code = (<CODE> == UMAX || <CODE> == UMIN) ? GTU : GT;
5930
5931   xops[3] = gen_rtx_fmt_ee (code, VOIDmode, operands[1], operands[2]);
5932   xops[4] = operands[1];
5933   xops[5] = operands[2];
5934
5935   ok = ix86_expand_int_vcond (xops);
5936   gcc_assert (ok);
5937   DONE;
5938 })
5939
5940 (define_expand "<code><mode>3"
5941   [(set (match_operand:VI124_128 0 "register_operand" "")
5942         (smaxmin:VI124_128
5943           (match_operand:VI124_128 1 "nonimmediate_operand" "")
5944           (match_operand:VI124_128 2 "nonimmediate_operand" "")))]
5945   "TARGET_SSE2"
5946 {
5947   if (TARGET_SSE4_1 || <MODE>mode == V8HImode)
5948     ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);
5949   else
5950     {
5951       rtx xops[6];
5952       bool ok;
5953
5954       xops[0] = operands[0];
5955       operands[1] = force_reg (<MODE>mode, operands[1]);
5956       operands[2] = force_reg (<MODE>mode, operands[2]);
5957
5958       if (<CODE> == SMAX)
5959         {
5960           xops[1] = operands[1];
5961           xops[2] = operands[2];
5962         }
5963       else
5964         {
5965           xops[1] = operands[2];
5966           xops[2] = operands[1];
5967         }
5968
5969       xops[3] = gen_rtx_GT (VOIDmode, operands[1], operands[2]);
5970       xops[4] = operands[1];
5971       xops[5] = operands[2];
5972
5973       ok = ix86_expand_int_vcond (xops);
5974       gcc_assert (ok);
5975       DONE;
5976     }
5977 })
5978
5979 (define_insn "*sse4_1_<code><mode>3"
5980   [(set (match_operand:VI14_128 0 "register_operand" "=x,x")
5981         (smaxmin:VI14_128
5982           (match_operand:VI14_128 1 "nonimmediate_operand" "%0,x")
5983           (match_operand:VI14_128 2 "nonimmediate_operand" "xm,xm")))]
5984   "TARGET_SSE4_1 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5985   "@
5986    p<maxmin_int><ssemodesuffix>\t{%2, %0|%0, %2}
5987    vp<maxmin_int><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
5988   [(set_attr "isa" "noavx,avx")
5989    (set_attr "type" "sseiadd")
5990    (set_attr "prefix_extra" "1,*")
5991    (set_attr "prefix" "orig,vex")
5992    (set_attr "mode" "TI")])
5993
5994 (define_insn "*<code>v8hi3"
5995   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
5996         (smaxmin:V8HI
5997           (match_operand:V8HI 1 "nonimmediate_operand" "%0,x")
5998           (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")))]
5999   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, V8HImode, operands)"
6000   "@
6001    p<maxmin_int>w\t{%2, %0|%0, %2}
6002    vp<maxmin_int>w\t{%2, %1, %0|%0, %1, %2}"
6003   [(set_attr "isa" "noavx,avx")
6004    (set_attr "type" "sseiadd")
6005    (set_attr "prefix_data16" "1,*")
6006    (set_attr "prefix_extra" "*,1")
6007    (set_attr "prefix" "orig,vex")
6008    (set_attr "mode" "TI")])
6009
6010 (define_expand "<code><mode>3"
6011   [(set (match_operand:VI124_128 0 "register_operand" "")
6012         (umaxmin:VI124_128
6013           (match_operand:VI124_128 1 "nonimmediate_operand" "")
6014           (match_operand:VI124_128 2 "nonimmediate_operand" "")))]
6015   "TARGET_SSE2"
6016 {
6017   if (TARGET_SSE4_1 || <MODE>mode == V16QImode)
6018     ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);
6019   else if (<CODE> == UMAX && <MODE>mode == V8HImode)
6020     {
6021       rtx op0 = operands[0], op2 = operands[2], op3 = op0;
6022       operands[1] = force_reg (<MODE>mode, operands[1]);
6023       if (rtx_equal_p (op3, op2))
6024         op3 = gen_reg_rtx (V8HImode);
6025       emit_insn (gen_sse2_ussubv8hi3 (op3, operands[1], op2));
6026       emit_insn (gen_addv8hi3 (op0, op3, op2));
6027       DONE;
6028     }
6029   else
6030     {
6031       rtx xops[6];
6032       bool ok;
6033
6034       operands[1] = force_reg (<MODE>mode, operands[1]);
6035       operands[2] = force_reg (<MODE>mode, operands[2]);
6036
6037       xops[0] = operands[0];
6038
6039       if (<CODE> == UMAX)
6040         {
6041           xops[1] = operands[1];
6042           xops[2] = operands[2];
6043         }
6044       else
6045         {
6046           xops[1] = operands[2];
6047           xops[2] = operands[1];
6048         }
6049
6050       xops[3] = gen_rtx_GTU (VOIDmode, operands[1], operands[2]);
6051       xops[4] = operands[1];
6052       xops[5] = operands[2];
6053
6054       ok = ix86_expand_int_vcond (xops);
6055       gcc_assert (ok);
6056       DONE;
6057     }
6058 })
6059
6060 (define_insn "*sse4_1_<code><mode>3"
6061   [(set (match_operand:VI24_128 0 "register_operand" "=x,x")
6062         (umaxmin:VI24_128
6063           (match_operand:VI24_128 1 "nonimmediate_operand" "%0,x")
6064           (match_operand:VI24_128 2 "nonimmediate_operand" "xm,xm")))]
6065   "TARGET_SSE4_1 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6066   "@
6067    p<maxmin_int><ssemodesuffix>\t{%2, %0|%0, %2}
6068    vp<maxmin_int><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
6069   [(set_attr "isa" "noavx,avx")
6070    (set_attr "type" "sseiadd")
6071    (set_attr "prefix_extra" "1,*")
6072    (set_attr "prefix" "orig,vex")
6073    (set_attr "mode" "TI")])
6074
6075 (define_insn "*<code>v16qi3"
6076   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
6077         (umaxmin:V16QI
6078           (match_operand:V16QI 1 "nonimmediate_operand" "%0,x")
6079           (match_operand:V16QI 2 "nonimmediate_operand" "xm,xm")))]
6080   "TARGET_SSE2 && ix86_binary_operator_ok (<CODE>, V16QImode, operands)"
6081   "@
6082    p<maxmin_int>b\t{%2, %0|%0, %2}
6083    vp<maxmin_int>b\t{%2, %1, %0|%0, %1, %2}"
6084   [(set_attr "isa" "noavx,avx")
6085    (set_attr "type" "sseiadd")
6086    (set_attr "prefix_data16" "1,*")
6087    (set_attr "prefix_extra" "*,1")
6088    (set_attr "prefix" "orig,vex")
6089    (set_attr "mode" "TI")])
6090
6091 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6092 ;;
6093 ;; Parallel integral comparisons
6094 ;;
6095 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6096
6097 (define_expand "avx2_eq<mode>3"
6098   [(set (match_operand:VI_256 0 "register_operand" "")
6099         (eq:VI_256
6100           (match_operand:VI_256 1 "nonimmediate_operand" "")
6101           (match_operand:VI_256 2 "nonimmediate_operand" "")))]
6102   "TARGET_AVX2"
6103   "ix86_fixup_binary_operands_no_copy (EQ, <MODE>mode, operands);")
6104
6105 (define_insn "*avx2_eq<mode>3"
6106   [(set (match_operand:VI_256 0 "register_operand" "=x")
6107         (eq:VI_256
6108           (match_operand:VI_256 1 "nonimmediate_operand" "%x")
6109           (match_operand:VI_256 2 "nonimmediate_operand" "xm")))]
6110   "TARGET_AVX2 && ix86_binary_operator_ok (EQ, <MODE>mode, operands)"
6111   "vpcmpeq<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
6112   [(set_attr "type" "ssecmp")
6113    (set_attr "prefix_extra" "1")
6114    (set_attr "prefix" "vex")
6115    (set_attr "mode" "OI")])
6116
6117 (define_insn "*sse4_1_eqv2di3"
6118   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
6119         (eq:V2DI
6120           (match_operand:V2DI 1 "nonimmediate_operand" "%0,x")
6121           (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")))]
6122   "TARGET_SSE4_1 && ix86_binary_operator_ok (EQ, V2DImode, operands)"
6123   "@
6124    pcmpeqq\t{%2, %0|%0, %2}
6125    vpcmpeqq\t{%2, %1, %0|%0, %1, %2}"
6126   [(set_attr "isa" "noavx,avx")
6127    (set_attr "type" "ssecmp")
6128    (set_attr "prefix_extra" "1")
6129    (set_attr "prefix" "orig,vex")
6130    (set_attr "mode" "TI")])
6131
6132 (define_insn "*sse2_eq<mode>3"
6133   [(set (match_operand:VI124_128 0 "register_operand" "=x,x")
6134         (eq:VI124_128
6135           (match_operand:VI124_128 1 "nonimmediate_operand" "%0,x")
6136           (match_operand:VI124_128 2 "nonimmediate_operand" "xm,xm")))]
6137   "TARGET_SSE2 && !TARGET_XOP
6138    && ix86_binary_operator_ok (EQ, <MODE>mode, operands)"
6139   "@
6140    pcmpeq<ssemodesuffix>\t{%2, %0|%0, %2}
6141    vpcmpeq<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
6142   [(set_attr "isa" "noavx,avx")
6143    (set_attr "type" "ssecmp")
6144    (set_attr "prefix_data16" "1,*")
6145    (set_attr "prefix" "orig,vex")
6146    (set_attr "mode" "TI")])
6147
6148 (define_expand "sse2_eq<mode>3"
6149   [(set (match_operand:VI124_128 0 "register_operand" "")
6150         (eq:VI124_128
6151           (match_operand:VI124_128 1 "nonimmediate_operand" "")
6152           (match_operand:VI124_128 2 "nonimmediate_operand" "")))]
6153   "TARGET_SSE2 && !TARGET_XOP "
6154   "ix86_fixup_binary_operands_no_copy (EQ, <MODE>mode, operands);")
6155
6156 (define_expand "sse4_1_eqv2di3"
6157   [(set (match_operand:V2DI 0 "register_operand" "")
6158         (eq:V2DI
6159           (match_operand:V2DI 1 "nonimmediate_operand" "")
6160           (match_operand:V2DI 2 "nonimmediate_operand" "")))]
6161   "TARGET_SSE4_1"
6162   "ix86_fixup_binary_operands_no_copy (EQ, V2DImode, operands);")
6163
6164 (define_insn "sse4_2_gtv2di3"
6165   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
6166         (gt:V2DI
6167           (match_operand:V2DI 1 "register_operand" "0,x")
6168           (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")))]
6169   "TARGET_SSE4_2"
6170   "@
6171    pcmpgtq\t{%2, %0|%0, %2}
6172    vpcmpgtq\t{%2, %1, %0|%0, %1, %2}"
6173   [(set_attr "isa" "noavx,avx")
6174    (set_attr "type" "ssecmp")
6175    (set_attr "prefix_extra" "1")
6176    (set_attr "prefix" "orig,vex")
6177    (set_attr "mode" "TI")])
6178
6179 (define_insn "avx2_gt<mode>3"
6180   [(set (match_operand:VI_256 0 "register_operand" "=x")
6181         (gt:VI_256
6182           (match_operand:VI_256 1 "register_operand" "x")
6183           (match_operand:VI_256 2 "nonimmediate_operand" "xm")))]
6184   "TARGET_AVX2"
6185   "vpcmpgt<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
6186   [(set_attr "type" "ssecmp")
6187    (set_attr "prefix_extra" "1")
6188    (set_attr "prefix" "vex")
6189    (set_attr "mode" "OI")])
6190
6191 (define_insn "sse2_gt<mode>3"
6192   [(set (match_operand:VI124_128 0 "register_operand" "=x,x")
6193         (gt:VI124_128
6194           (match_operand:VI124_128 1 "register_operand" "0,x")
6195           (match_operand:VI124_128 2 "nonimmediate_operand" "xm,xm")))]
6196   "TARGET_SSE2 && !TARGET_XOP"
6197   "@
6198    pcmpgt<ssemodesuffix>\t{%2, %0|%0, %2}
6199    vpcmpgt<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
6200   [(set_attr "isa" "noavx,avx")
6201    (set_attr "type" "ssecmp")
6202    (set_attr "prefix_data16" "1,*")
6203    (set_attr "prefix" "orig,vex")
6204    (set_attr "mode" "TI")])
6205
6206 (define_expand "vcond<V_256:mode><VI_256:mode>"
6207   [(set (match_operand:V_256 0 "register_operand" "")
6208         (if_then_else:V_256
6209           (match_operator 3 ""
6210             [(match_operand:VI_256 4 "nonimmediate_operand" "")
6211              (match_operand:VI_256 5 "nonimmediate_operand" "")])
6212           (match_operand:V_256 1 "general_operand" "")
6213           (match_operand:V_256 2 "general_operand" "")))]
6214   "TARGET_AVX2
6215    && (GET_MODE_NUNITS (<V_256:MODE>mode)
6216        == GET_MODE_NUNITS (<VI_256:MODE>mode))"
6217 {
6218   bool ok = ix86_expand_int_vcond (operands);
6219   gcc_assert (ok);
6220   DONE;
6221 })
6222
6223 (define_expand "vcond<V_128:mode><VI124_128:mode>"
6224   [(set (match_operand:V_128 0 "register_operand" "")
6225         (if_then_else:V_128
6226           (match_operator 3 ""
6227             [(match_operand:VI124_128 4 "nonimmediate_operand" "")
6228              (match_operand:VI124_128 5 "nonimmediate_operand" "")])
6229           (match_operand:V_128 1 "general_operand" "")
6230           (match_operand:V_128 2 "general_operand" "")))]
6231   "TARGET_SSE2
6232    && (GET_MODE_NUNITS (<V_128:MODE>mode)
6233        == GET_MODE_NUNITS (<VI124_128:MODE>mode))"
6234 {
6235   bool ok = ix86_expand_int_vcond (operands);
6236   gcc_assert (ok);
6237   DONE;
6238 })
6239
6240 (define_expand "vcond<VI8F_128:mode>v2di"
6241   [(set (match_operand:VI8F_128 0 "register_operand" "")
6242         (if_then_else:VI8F_128
6243           (match_operator 3 ""
6244             [(match_operand:V2DI 4 "nonimmediate_operand" "")
6245              (match_operand:V2DI 5 "nonimmediate_operand" "")])
6246           (match_operand:VI8F_128 1 "general_operand" "")
6247           (match_operand:VI8F_128 2 "general_operand" "")))]
6248   "TARGET_SSE4_2"
6249 {
6250   bool ok = ix86_expand_int_vcond (operands);
6251   gcc_assert (ok);
6252   DONE;
6253 })
6254
6255 (define_expand "vcondu<V_256:mode><VI_256:mode>"
6256   [(set (match_operand:V_256 0 "register_operand" "")
6257         (if_then_else:V_256
6258           (match_operator 3 ""
6259             [(match_operand:VI_256 4 "nonimmediate_operand" "")
6260              (match_operand:VI_256 5 "nonimmediate_operand" "")])
6261           (match_operand:V_256 1 "general_operand" "")
6262           (match_operand:V_256 2 "general_operand" "")))]
6263   "TARGET_AVX2
6264    && (GET_MODE_NUNITS (<V_256:MODE>mode)
6265        == GET_MODE_NUNITS (<VI_256:MODE>mode))"
6266 {
6267   bool ok = ix86_expand_int_vcond (operands);
6268   gcc_assert (ok);
6269   DONE;
6270 })
6271
6272 (define_expand "vcondu<V_128:mode><VI124_128:mode>"
6273   [(set (match_operand:V_128 0 "register_operand" "")
6274         (if_then_else:V_128
6275           (match_operator 3 ""
6276             [(match_operand:VI124_128 4 "nonimmediate_operand" "")
6277              (match_operand:VI124_128 5 "nonimmediate_operand" "")])
6278           (match_operand:V_128 1 "general_operand" "")
6279           (match_operand:V_128 2 "general_operand" "")))]
6280   "TARGET_SSE2
6281    && (GET_MODE_NUNITS (<V_128:MODE>mode)
6282        == GET_MODE_NUNITS (<VI124_128:MODE>mode))"
6283 {
6284   bool ok = ix86_expand_int_vcond (operands);
6285   gcc_assert (ok);
6286   DONE;
6287 })
6288
6289 (define_expand "vcondu<VI8F_128:mode>v2di"
6290   [(set (match_operand:VI8F_128 0 "register_operand" "")
6291         (if_then_else:VI8F_128
6292           (match_operator 3 ""
6293             [(match_operand:V2DI 4 "nonimmediate_operand" "")
6294              (match_operand:V2DI 5 "nonimmediate_operand" "")])
6295           (match_operand:VI8F_128 1 "general_operand" "")
6296           (match_operand:VI8F_128 2 "general_operand" "")))]
6297   "TARGET_SSE4_2"
6298 {
6299   bool ok = ix86_expand_int_vcond (operands);
6300   gcc_assert (ok);
6301   DONE;
6302 })
6303
6304 (define_mode_iterator VEC_PERM_AVX2
6305   [V16QI V8HI V4SI V2DI V4SF V2DF
6306    (V32QI "TARGET_AVX2") (V16HI "TARGET_AVX2")
6307    (V8SI "TARGET_AVX2") (V4DI "TARGET_AVX2")
6308    (V8SF "TARGET_AVX2") (V4DF "TARGET_AVX2")])
6309
6310 (define_expand "vec_perm<mode>"
6311   [(match_operand:VEC_PERM_AVX2 0 "register_operand" "")
6312    (match_operand:VEC_PERM_AVX2 1 "register_operand" "")
6313    (match_operand:VEC_PERM_AVX2 2 "register_operand" "")
6314    (match_operand:<sseintvecmode> 3 "register_operand" "")]
6315   "TARGET_SSSE3 || TARGET_AVX || TARGET_XOP"
6316 {
6317   ix86_expand_vec_perm (operands);
6318   DONE;
6319 })
6320
6321 (define_mode_iterator VEC_PERM_CONST
6322   [(V4SF "TARGET_SSE") (V4SI "TARGET_SSE")
6323    (V2DF "TARGET_SSE") (V2DI "TARGET_SSE")
6324    (V16QI "TARGET_SSE2") (V8HI "TARGET_SSE2")
6325    (V8SF "TARGET_AVX") (V4DF "TARGET_AVX")
6326    (V8SI "TARGET_AVX") (V4DI "TARGET_AVX")
6327    (V32QI "TARGET_AVX2") (V16HI "TARGET_AVX2")])
6328
6329 (define_expand "vec_perm_const<mode>"
6330   [(match_operand:VEC_PERM_CONST 0 "register_operand" "")
6331    (match_operand:VEC_PERM_CONST 1 "register_operand" "")
6332    (match_operand:VEC_PERM_CONST 2 "register_operand" "")
6333    (match_operand:<sseintvecmode> 3 "" "")]
6334   ""
6335 {
6336   if (ix86_expand_vec_perm_const (operands))
6337     DONE;
6338   else
6339     FAIL;
6340 })
6341
6342 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6343 ;;
6344 ;; Parallel bitwise logical operations
6345 ;;
6346 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6347
6348 (define_expand "one_cmpl<mode>2"
6349   [(set (match_operand:VI 0 "register_operand" "")
6350         (xor:VI (match_operand:VI 1 "nonimmediate_operand" "")
6351                 (match_dup 2)))]
6352   "TARGET_SSE"
6353 {
6354   int i, n = GET_MODE_NUNITS (<MODE>mode);
6355   rtvec v = rtvec_alloc (n);
6356
6357   for (i = 0; i < n; ++i)
6358     RTVEC_ELT (v, i) = constm1_rtx;
6359
6360   operands[2] = force_reg (<MODE>mode, gen_rtx_CONST_VECTOR (<MODE>mode, v));
6361 })
6362
6363 (define_expand "<sse2_avx2>_andnot<mode>3"
6364   [(set (match_operand:VI_AVX2 0 "register_operand" "")
6365         (and:VI_AVX2
6366           (not:VI_AVX2 (match_operand:VI_AVX2 1 "register_operand" ""))
6367           (match_operand:VI_AVX2 2 "nonimmediate_operand" "")))]
6368   "TARGET_SSE2")
6369
6370 (define_insn "*andnot<mode>3"
6371   [(set (match_operand:VI 0 "register_operand" "=x,x")
6372         (and:VI
6373           (not:VI (match_operand:VI 1 "register_operand" "0,x"))
6374           (match_operand:VI 2 "nonimmediate_operand" "xm,xm")))]
6375   "TARGET_SSE"
6376 {
6377   static char buf[32];
6378   const char *ops;
6379   const char *tmp;
6380
6381   switch (get_attr_mode (insn))
6382     {
6383     case MODE_OI:
6384       gcc_assert (TARGET_AVX2);
6385     case MODE_TI:
6386       gcc_assert (TARGET_SSE2);
6387
6388       tmp = "pandn";
6389       break;
6390
6391    case MODE_V8SF:
6392       gcc_assert (TARGET_AVX);
6393    case MODE_V4SF:
6394       gcc_assert (TARGET_SSE);
6395
6396       tmp = "andnps";
6397       break;
6398
6399    default:
6400       gcc_unreachable ();
6401    }
6402
6403   switch (which_alternative)
6404     {
6405     case 0:
6406       ops = "%s\t{%%2, %%0|%%0, %%2}";
6407       break;
6408     case 1:
6409       ops = "v%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
6410       break;
6411     default:
6412       gcc_unreachable ();
6413     }
6414
6415   snprintf (buf, sizeof (buf), ops, tmp);
6416   return buf;
6417 }
6418   [(set_attr "isa" "noavx,avx")
6419    (set_attr "type" "sselog")
6420    (set (attr "prefix_data16")
6421      (if_then_else
6422        (and (eq_attr "alternative" "0")
6423             (eq_attr "mode" "TI"))
6424        (const_string "1")
6425        (const_string "*")))
6426    (set_attr "prefix" "orig,vex")
6427    (set (attr "mode")
6428      (cond [(and (not (match_test "TARGET_AVX2"))
6429                  (match_test "GET_MODE_SIZE (<MODE>mode) > 16"))
6430               (const_string "V8SF")
6431             (not (match_test "TARGET_SSE2"))
6432               (const_string "V4SF")
6433            ]
6434            (const_string "<sseinsnmode>")))])
6435
6436 (define_expand "<code><mode>3"
6437   [(set (match_operand:VI 0 "register_operand" "")
6438         (any_logic:VI
6439           (match_operand:VI 1 "nonimmediate_operand" "")
6440           (match_operand:VI 2 "nonimmediate_operand" "")))]
6441   "TARGET_SSE"
6442   "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
6443
6444 (define_insn "*<code><mode>3"
6445   [(set (match_operand:VI 0 "register_operand" "=x,x")
6446         (any_logic:VI
6447           (match_operand:VI 1 "nonimmediate_operand" "%0,x")
6448           (match_operand:VI 2 "nonimmediate_operand" "xm,xm")))]
6449   "TARGET_SSE
6450    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6451 {
6452   static char buf[32];
6453   const char *ops;
6454   const char *tmp;
6455
6456   switch (get_attr_mode (insn))
6457     {
6458     case MODE_OI:
6459       gcc_assert (TARGET_AVX2);
6460     case MODE_TI:
6461       gcc_assert (TARGET_SSE2);
6462
6463       tmp = "p<logic>";
6464       break;
6465
6466    case MODE_V8SF:
6467       gcc_assert (TARGET_AVX);
6468    case MODE_V4SF:
6469       gcc_assert (TARGET_SSE);
6470
6471       tmp = "<logic>ps";
6472       break;
6473
6474    default:
6475       gcc_unreachable ();
6476    }
6477
6478   switch (which_alternative)
6479     {
6480     case 0:
6481       ops = "%s\t{%%2, %%0|%%0, %%2}";
6482       break;
6483     case 1:
6484       ops = "v%s\t{%%2, %%1, %%0|%%0, %%1, %%2}";
6485       break;
6486     default:
6487       gcc_unreachable ();
6488     }
6489
6490   snprintf (buf, sizeof (buf), ops, tmp);
6491   return buf;
6492 }
6493   [(set_attr "isa" "noavx,avx")
6494    (set_attr "type" "sselog")
6495    (set (attr "prefix_data16")
6496      (if_then_else
6497        (and (eq_attr "alternative" "0")
6498             (eq_attr "mode" "TI"))
6499        (const_string "1")
6500        (const_string "*")))
6501    (set_attr "prefix" "orig,vex")
6502    (set (attr "mode")
6503      (cond [(and (not (match_test "TARGET_AVX2"))
6504                  (match_test "GET_MODE_SIZE (<MODE>mode) > 16"))
6505               (const_string "V8SF")
6506             (not (match_test "TARGET_SSE2"))
6507               (const_string "V4SF")
6508            ]
6509            (const_string "<sseinsnmode>")))])
6510
6511 (define_insn "*andnottf3"
6512   [(set (match_operand:TF 0 "register_operand" "=x,x")
6513         (and:TF
6514           (not:TF (match_operand:TF 1 "register_operand" "0,x"))
6515           (match_operand:TF 2 "nonimmediate_operand" "xm,xm")))]
6516   "TARGET_SSE2"
6517   "@
6518    pandn\t{%2, %0|%0, %2}
6519    vpandn\t{%2, %1, %0|%0, %1, %2}"
6520   [(set_attr "isa" "noavx,avx")
6521    (set_attr "type" "sselog")
6522    (set_attr "prefix_data16" "1,*")
6523    (set_attr "prefix" "orig,vex")
6524    (set_attr "mode" "TI")])
6525
6526 (define_expand "<code>tf3"
6527   [(set (match_operand:TF 0 "register_operand" "")
6528         (any_logic:TF
6529           (match_operand:TF 1 "nonimmediate_operand" "")
6530           (match_operand:TF 2 "nonimmediate_operand" "")))]
6531   "TARGET_SSE2"
6532   "ix86_fixup_binary_operands_no_copy (<CODE>, TFmode, operands);")
6533
6534 (define_insn "*<code>tf3"
6535   [(set (match_operand:TF 0 "register_operand" "=x,x")
6536         (any_logic:TF
6537           (match_operand:TF 1 "nonimmediate_operand" "%0,x")
6538           (match_operand:TF 2 "nonimmediate_operand" "xm,xm")))]
6539   "TARGET_SSE2
6540    && ix86_binary_operator_ok (<CODE>, TFmode, operands)"
6541   "@
6542    p<logic>\t{%2, %0|%0, %2}
6543    vp<logic>\t{%2, %1, %0|%0, %1, %2}"
6544   [(set_attr "isa" "noavx,avx")
6545    (set_attr "type" "sselog")
6546    (set_attr "prefix_data16" "1,*")
6547    (set_attr "prefix" "orig,vex")
6548    (set_attr "mode" "TI")])
6549
6550 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6551 ;;
6552 ;; Parallel integral element swizzling
6553 ;;
6554 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
6555
6556 (define_expand "vec_pack_trunc_<mode>"
6557   [(match_operand:<ssepackmode> 0 "register_operand" "")
6558    (match_operand:VI248_AVX2 1 "register_operand" "")
6559    (match_operand:VI248_AVX2 2 "register_operand" "")]
6560   "TARGET_SSE2"
6561 {
6562   rtx op1 = gen_lowpart (<ssepackmode>mode, operands[1]);
6563   rtx op2 = gen_lowpart (<ssepackmode>mode, operands[2]);
6564   ix86_expand_vec_extract_even_odd (operands[0], op1, op2, 0);
6565   DONE;
6566 })
6567
6568 (define_insn "<sse2_avx2>_packsswb"
6569   [(set (match_operand:VI1_AVX2 0 "register_operand" "=x,x")
6570         (vec_concat:VI1_AVX2
6571           (ss_truncate:<ssehalfvecmode>
6572             (match_operand:<sseunpackmode> 1 "register_operand" "0,x"))
6573           (ss_truncate:<ssehalfvecmode>
6574             (match_operand:<sseunpackmode> 2 "nonimmediate_operand" "xm,xm"))))]
6575   "TARGET_SSE2"
6576   "@
6577    packsswb\t{%2, %0|%0, %2}
6578    vpacksswb\t{%2, %1, %0|%0, %1, %2}"
6579   [(set_attr "isa" "noavx,avx")
6580    (set_attr "type" "sselog")
6581    (set_attr "prefix_data16" "1,*")
6582    (set_attr "prefix" "orig,vex")
6583    (set_attr "mode" "<sseinsnmode>")])
6584
6585 (define_insn "<sse2_avx2>_packssdw"
6586   [(set (match_operand:VI2_AVX2 0 "register_operand" "=x,x")
6587         (vec_concat:VI2_AVX2
6588           (ss_truncate:<ssehalfvecmode>
6589             (match_operand:<sseunpackmode> 1 "register_operand" "0,x"))
6590           (ss_truncate:<ssehalfvecmode>
6591             (match_operand:<sseunpackmode> 2 "nonimmediate_operand" "xm,xm"))))]
6592   "TARGET_SSE2"
6593   "@
6594    packssdw\t{%2, %0|%0, %2}
6595    vpackssdw\t{%2, %1, %0|%0, %1, %2}"
6596   [(set_attr "isa" "noavx,avx")
6597    (set_attr "type" "sselog")
6598    (set_attr "prefix_data16" "1,*")
6599    (set_attr "prefix" "orig,vex")
6600    (set_attr "mode" "<sseinsnmode>")])
6601
6602 (define_insn "<sse2_avx2>_packuswb"
6603   [(set (match_operand:VI1_AVX2 0 "register_operand" "=x,x")
6604         (vec_concat:VI1_AVX2
6605           (us_truncate:<ssehalfvecmode>
6606             (match_operand:<sseunpackmode> 1 "register_operand" "0,x"))
6607           (us_truncate:<ssehalfvecmode>
6608             (match_operand:<sseunpackmode> 2 "nonimmediate_operand" "xm,xm"))))]
6609   "TARGET_SSE2"
6610   "@
6611    packuswb\t{%2, %0|%0, %2}
6612    vpackuswb\t{%2, %1, %0|%0, %1, %2}"
6613   [(set_attr "isa" "noavx,avx")
6614    (set_attr "type" "sselog")
6615    (set_attr "prefix_data16" "1,*")
6616    (set_attr "prefix" "orig,vex")
6617    (set_attr "mode" "<sseinsnmode>")])
6618
6619 (define_insn "avx2_interleave_highv32qi"
6620   [(set (match_operand:V32QI 0 "register_operand" "=x")
6621         (vec_select:V32QI
6622           (vec_concat:V64QI
6623             (match_operand:V32QI 1 "register_operand" "x")
6624             (match_operand:V32QI 2 "nonimmediate_operand" "xm"))
6625           (parallel [(const_int 8)  (const_int 40)
6626                      (const_int 9)  (const_int 41)
6627                      (const_int 10) (const_int 42)
6628                      (const_int 11) (const_int 43)
6629                      (const_int 12) (const_int 44)
6630                      (const_int 13) (const_int 45)
6631                      (const_int 14) (const_int 46)
6632                      (const_int 15) (const_int 47)
6633                      (const_int 24) (const_int 56)
6634                      (const_int 25) (const_int 57)
6635                      (const_int 26) (const_int 58)
6636                      (const_int 27) (const_int 59)
6637                      (const_int 28) (const_int 60)
6638                      (const_int 29) (const_int 61)
6639                      (const_int 30) (const_int 62)
6640                      (const_int 31) (const_int 63)])))]
6641   "TARGET_AVX2"
6642   "vpunpckhbw\t{%2, %1, %0|%0, %1, %2}"
6643   [(set_attr "type" "sselog")
6644    (set_attr "prefix" "vex")
6645    (set_attr "mode" "OI")])
6646
6647 (define_insn "vec_interleave_highv16qi"
6648   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
6649         (vec_select:V16QI
6650           (vec_concat:V32QI
6651             (match_operand:V16QI 1 "register_operand" "0,x")
6652             (match_operand:V16QI 2 "nonimmediate_operand" "xm,xm"))
6653           (parallel [(const_int 8)  (const_int 24)
6654                      (const_int 9)  (const_int 25)
6655                      (const_int 10) (const_int 26)
6656                      (const_int 11) (const_int 27)
6657                      (const_int 12) (const_int 28)
6658                      (const_int 13) (const_int 29)
6659                      (const_int 14) (const_int 30)
6660                      (const_int 15) (const_int 31)])))]
6661   "TARGET_SSE2"
6662   "@
6663    punpckhbw\t{%2, %0|%0, %2}
6664    vpunpckhbw\t{%2, %1, %0|%0, %1, %2}"
6665   [(set_attr "isa" "noavx,avx")
6666    (set_attr "type" "sselog")
6667    (set_attr "prefix_data16" "1,*")
6668    (set_attr "prefix" "orig,vex")
6669    (set_attr "mode" "TI")])
6670
6671 (define_insn "avx2_interleave_lowv32qi"
6672   [(set (match_operand:V32QI 0 "register_operand" "=x")
6673         (vec_select:V32QI
6674           (vec_concat:V64QI
6675             (match_operand:V32QI 1 "register_operand" "x")
6676             (match_operand:V32QI 2 "nonimmediate_operand" "xm"))
6677           (parallel [(const_int 0) (const_int 32)
6678                      (const_int 1) (const_int 33)
6679                      (const_int 2) (const_int 34)
6680                      (const_int 3) (const_int 35)
6681                      (const_int 4) (const_int 36)
6682                      (const_int 5) (const_int 37)
6683                      (const_int 6) (const_int 38)
6684                      (const_int 7) (const_int 39)
6685                      (const_int 16) (const_int 48)
6686                      (const_int 17) (const_int 49)
6687                      (const_int 18) (const_int 50)
6688                      (const_int 19) (const_int 51)
6689                      (const_int 20) (const_int 52)
6690                      (const_int 21) (const_int 53)
6691                      (const_int 22) (const_int 54)
6692                      (const_int 23) (const_int 55)])))]
6693   "TARGET_AVX2"
6694   "vpunpcklbw\t{%2, %1, %0|%0, %1, %2}"
6695   [(set_attr "type" "sselog")
6696    (set_attr "prefix" "vex")
6697    (set_attr "mode" "OI")])
6698
6699 (define_insn "vec_interleave_lowv16qi"
6700   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
6701         (vec_select:V16QI
6702           (vec_concat:V32QI
6703             (match_operand:V16QI 1 "register_operand" "0,x")
6704             (match_operand:V16QI 2 "nonimmediate_operand" "xm,xm"))
6705           (parallel [(const_int 0) (const_int 16)
6706                      (const_int 1) (const_int 17)
6707                      (const_int 2) (const_int 18)
6708                      (const_int 3) (const_int 19)
6709                      (const_int 4) (const_int 20)
6710                      (const_int 5) (const_int 21)
6711                      (const_int 6) (const_int 22)
6712                      (const_int 7) (const_int 23)])))]
6713   "TARGET_SSE2"
6714   "@
6715    punpcklbw\t{%2, %0|%0, %2}
6716    vpunpcklbw\t{%2, %1, %0|%0, %1, %2}"
6717   [(set_attr "isa" "noavx,avx")
6718    (set_attr "type" "sselog")
6719    (set_attr "prefix_data16" "1,*")
6720    (set_attr "prefix" "orig,vex")
6721    (set_attr "mode" "TI")])
6722
6723 (define_insn "avx2_interleave_highv16hi"
6724   [(set (match_operand:V16HI 0 "register_operand" "=x")
6725         (vec_select:V16HI
6726           (vec_concat:V32HI
6727             (match_operand:V16HI 1 "register_operand" "x")
6728             (match_operand:V16HI 2 "nonimmediate_operand" "xm"))
6729           (parallel [(const_int 4) (const_int 20)
6730                      (const_int 5) (const_int 21)
6731                      (const_int 6) (const_int 22)
6732                      (const_int 7) (const_int 23)
6733                      (const_int 12) (const_int 28)
6734                      (const_int 13) (const_int 29)
6735                      (const_int 14) (const_int 30)
6736                      (const_int 15) (const_int 31)])))]
6737   "TARGET_AVX2"
6738   "vpunpckhwd\t{%2, %1, %0|%0, %1, %2}"
6739   [(set_attr "type" "sselog")
6740    (set_attr "prefix" "vex")
6741    (set_attr "mode" "OI")])
6742
6743 (define_insn "vec_interleave_highv8hi"
6744   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
6745         (vec_select:V8HI
6746           (vec_concat:V16HI
6747             (match_operand:V8HI 1 "register_operand" "0,x")
6748             (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm"))
6749           (parallel [(const_int 4) (const_int 12)
6750                      (const_int 5) (const_int 13)
6751                      (const_int 6) (const_int 14)
6752                      (const_int 7) (const_int 15)])))]
6753   "TARGET_SSE2"
6754   "@
6755    punpckhwd\t{%2, %0|%0, %2}
6756    vpunpckhwd\t{%2, %1, %0|%0, %1, %2}"
6757   [(set_attr "isa" "noavx,avx")
6758    (set_attr "type" "sselog")
6759    (set_attr "prefix_data16" "1,*")
6760    (set_attr "prefix" "orig,vex")
6761    (set_attr "mode" "TI")])
6762
6763 (define_insn "avx2_interleave_lowv16hi"
6764   [(set (match_operand:V16HI 0 "register_operand" "=x")
6765         (vec_select:V16HI
6766           (vec_concat:V32HI
6767             (match_operand:V16HI 1 "register_operand" "x")
6768             (match_operand:V16HI 2 "nonimmediate_operand" "xm"))
6769           (parallel [(const_int 0) (const_int 16)
6770                      (const_int 1) (const_int 17)
6771                      (const_int 2) (const_int 18)
6772                      (const_int 3) (const_int 19)
6773                      (const_int 8) (const_int 24)
6774                      (const_int 9) (const_int 25)
6775                      (const_int 10) (const_int 26)
6776                      (const_int 11) (const_int 27)])))]
6777   "TARGET_AVX2"
6778   "vpunpcklwd\t{%2, %1, %0|%0, %1, %2}"
6779   [(set_attr "type" "sselog")
6780    (set_attr "prefix" "vex")
6781    (set_attr "mode" "OI")])
6782
6783 (define_insn "vec_interleave_lowv8hi"
6784   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
6785         (vec_select:V8HI
6786           (vec_concat:V16HI
6787             (match_operand:V8HI 1 "register_operand" "0,x")
6788             (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm"))
6789           (parallel [(const_int 0) (const_int 8)
6790                      (const_int 1) (const_int 9)
6791                      (const_int 2) (const_int 10)
6792                      (const_int 3) (const_int 11)])))]
6793   "TARGET_SSE2"
6794   "@
6795    punpcklwd\t{%2, %0|%0, %2}
6796    vpunpcklwd\t{%2, %1, %0|%0, %1, %2}"
6797   [(set_attr "isa" "noavx,avx")
6798    (set_attr "type" "sselog")
6799    (set_attr "prefix_data16" "1,*")
6800    (set_attr "prefix" "orig,vex")
6801    (set_attr "mode" "TI")])
6802
6803 (define_insn "avx2_interleave_highv8si"
6804   [(set (match_operand:V8SI 0 "register_operand" "=x")
6805         (vec_select:V8SI
6806           (vec_concat:V16SI
6807             (match_operand:V8SI 1 "register_operand" "x")
6808             (match_operand:V8SI 2 "nonimmediate_operand" "xm"))
6809           (parallel [(const_int 2) (const_int 10)
6810                      (const_int 3) (const_int 11)
6811                      (const_int 6) (const_int 14)
6812                      (const_int 7) (const_int 15)])))]
6813   "TARGET_AVX2"
6814   "vpunpckhdq\t{%2, %1, %0|%0, %1, %2}"
6815   [(set_attr "type" "sselog")
6816    (set_attr "prefix" "vex")
6817    (set_attr "mode" "OI")])
6818
6819 (define_insn "vec_interleave_highv4si"
6820   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
6821         (vec_select:V4SI
6822           (vec_concat:V8SI
6823             (match_operand:V4SI 1 "register_operand" "0,x")
6824             (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm"))
6825           (parallel [(const_int 2) (const_int 6)
6826                      (const_int 3) (const_int 7)])))]
6827   "TARGET_SSE2"
6828   "@
6829    punpckhdq\t{%2, %0|%0, %2}
6830    vpunpckhdq\t{%2, %1, %0|%0, %1, %2}"
6831   [(set_attr "isa" "noavx,avx")
6832    (set_attr "type" "sselog")
6833    (set_attr "prefix_data16" "1,*")
6834    (set_attr "prefix" "orig,vex")
6835    (set_attr "mode" "TI")])
6836
6837 (define_insn "avx2_interleave_lowv8si"
6838   [(set (match_operand:V8SI 0 "register_operand" "=x")
6839         (vec_select:V8SI
6840           (vec_concat:V16SI
6841             (match_operand:V8SI 1 "register_operand" "x")
6842             (match_operand:V8SI 2 "nonimmediate_operand" "xm"))
6843           (parallel [(const_int 0) (const_int 8)
6844                      (const_int 1) (const_int 9)
6845                      (const_int 4) (const_int 12)
6846                      (const_int 5) (const_int 13)])))]
6847   "TARGET_AVX2"
6848   "vpunpckldq\t{%2, %1, %0|%0, %1, %2}"
6849   [(set_attr "type" "sselog")
6850    (set_attr "prefix" "vex")
6851    (set_attr "mode" "OI")])
6852
6853 (define_insn "vec_interleave_lowv4si"
6854   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
6855         (vec_select:V4SI
6856           (vec_concat:V8SI
6857             (match_operand:V4SI 1 "register_operand" "0,x")
6858             (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm"))
6859           (parallel [(const_int 0) (const_int 4)
6860                      (const_int 1) (const_int 5)])))]
6861   "TARGET_SSE2"
6862   "@
6863    punpckldq\t{%2, %0|%0, %2}
6864    vpunpckldq\t{%2, %1, %0|%0, %1, %2}"
6865   [(set_attr "isa" "noavx,avx")
6866    (set_attr "type" "sselog")
6867    (set_attr "prefix_data16" "1,*")
6868    (set_attr "prefix" "orig,vex")
6869    (set_attr "mode" "TI")])
6870
6871 (define_expand "vec_interleave_high<mode>"
6872   [(match_operand:VI_256 0 "register_operand" "=x")
6873    (match_operand:VI_256 1 "register_operand" "x")
6874    (match_operand:VI_256 2 "nonimmediate_operand" "xm")]
6875  "TARGET_AVX2"
6876 {
6877   rtx t1 = gen_reg_rtx (<MODE>mode);
6878   rtx t2 = gen_reg_rtx (<MODE>mode);
6879   emit_insn (gen_avx2_interleave_low<mode> (t1, operands[1], operands[2]));
6880   emit_insn (gen_avx2_interleave_high<mode> (t2,  operands[1], operands[2]));
6881   emit_insn (gen_avx2_permv2ti (gen_lowpart (V4DImode, operands[0]),
6882                                 gen_lowpart (V4DImode, t1),
6883                                 gen_lowpart (V4DImode, t2), GEN_INT (1 + (3 << 4))));
6884   DONE;
6885 })
6886
6887 (define_expand "vec_interleave_low<mode>"
6888   [(match_operand:VI_256 0 "register_operand" "=x")
6889    (match_operand:VI_256 1 "register_operand" "x")
6890    (match_operand:VI_256 2 "nonimmediate_operand" "xm")]
6891  "TARGET_AVX2"
6892 {
6893   rtx t1 = gen_reg_rtx (<MODE>mode);
6894   rtx t2 = gen_reg_rtx (<MODE>mode);
6895   emit_insn (gen_avx2_interleave_low<mode> (t1, operands[1], operands[2]));
6896   emit_insn (gen_avx2_interleave_high<mode> (t2, operands[1], operands[2]));
6897   emit_insn (gen_avx2_permv2ti (gen_lowpart (V4DImode, operands[0]),
6898                                 gen_lowpart (V4DImode, t1),
6899                                 gen_lowpart (V4DImode, t2), GEN_INT (0 + (2 << 4))));
6900   DONE;
6901 })
6902
6903 ;; Modes handled by pinsr patterns.
6904 (define_mode_iterator PINSR_MODE
6905   [(V16QI "TARGET_SSE4_1") V8HI
6906    (V4SI "TARGET_SSE4_1")
6907    (V2DI "TARGET_SSE4_1 && TARGET_64BIT")])
6908
6909 (define_mode_attr sse2p4_1
6910   [(V16QI "sse4_1") (V8HI "sse2")
6911    (V4SI "sse4_1") (V2DI "sse4_1")])
6912
6913 ;; sse4_1_pinsrd must come before sse2_loadld since it is preferred.
6914 (define_insn "<sse2p4_1>_pinsr<ssemodesuffix>"
6915   [(set (match_operand:PINSR_MODE 0 "register_operand" "=x,x,x,x")
6916         (vec_merge:PINSR_MODE
6917           (vec_duplicate:PINSR_MODE
6918             (match_operand:<ssescalarmode> 2 "nonimmediate_operand" "r,m,r,m"))
6919           (match_operand:PINSR_MODE 1 "register_operand" "0,0,x,x")
6920           (match_operand:SI 3 "const_int_operand" "")))]
6921   "TARGET_SSE2
6922    && ((unsigned) exact_log2 (INTVAL (operands[3]))
6923        < GET_MODE_NUNITS (<MODE>mode))"
6924 {
6925   operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
6926
6927   switch (which_alternative)
6928     {
6929     case 0:
6930       if (GET_MODE_SIZE (<ssescalarmode>mode) < GET_MODE_SIZE (SImode))
6931         return "pinsr<ssemodesuffix>\t{%3, %k2, %0|%0, %k2, %3}";
6932       /* FALLTHRU */
6933     case 1:
6934       return "pinsr<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}";
6935     case 2:
6936       if (GET_MODE_SIZE (<ssescalarmode>mode) < GET_MODE_SIZE (SImode))
6937         return "vpinsr<ssemodesuffix>\t{%3, %k2, %1, %0|%0, %1, %k2, %3}";
6938       /* FALLTHRU */
6939     case 3:
6940       return "vpinsr<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}";
6941     default:
6942       gcc_unreachable ();
6943     }
6944 }
6945   [(set_attr "isa" "noavx,noavx,avx,avx")
6946    (set_attr "type" "sselog")
6947    (set (attr "prefix_rex")
6948      (if_then_else
6949        (and (not (match_test "TARGET_AVX"))
6950             (eq (const_string "<MODE>mode") (const_string "V2DImode")))
6951        (const_string "1")
6952        (const_string "*")))
6953    (set (attr "prefix_data16")
6954      (if_then_else
6955        (and (not (match_test "TARGET_AVX"))
6956             (eq (const_string "<MODE>mode") (const_string "V8HImode")))
6957        (const_string "1")
6958        (const_string "*")))
6959    (set (attr "prefix_extra")
6960      (if_then_else
6961        (and (not (match_test "TARGET_AVX"))
6962             (eq (const_string "<MODE>mode") (const_string "V8HImode")))
6963        (const_string "*")
6964        (const_string "1")))
6965    (set_attr "length_immediate" "1")
6966    (set_attr "prefix" "orig,orig,vex,vex")
6967    (set_attr "mode" "TI")])
6968
6969 (define_insn "*sse4_1_pextrb_<mode>"
6970   [(set (match_operand:SWI48 0 "register_operand" "=r")
6971         (zero_extend:SWI48
6972           (vec_select:QI
6973             (match_operand:V16QI 1 "register_operand" "x")
6974             (parallel [(match_operand:SI 2 "const_0_to_15_operand" "n")]))))]
6975   "TARGET_SSE4_1"
6976   "%vpextrb\t{%2, %1, %k0|%k0, %1, %2}"
6977   [(set_attr "type" "sselog")
6978    (set_attr "prefix_extra" "1")
6979    (set_attr "length_immediate" "1")
6980    (set_attr "prefix" "maybe_vex")
6981    (set_attr "mode" "TI")])
6982
6983 (define_insn "*sse4_1_pextrb_memory"
6984   [(set (match_operand:QI 0 "memory_operand" "=m")
6985         (vec_select:QI
6986           (match_operand:V16QI 1 "register_operand" "x")
6987           (parallel [(match_operand:SI 2 "const_0_to_15_operand" "n")])))]
6988   "TARGET_SSE4_1"
6989   "%vpextrb\t{%2, %1, %0|%0, %1, %2}"
6990   [(set_attr "type" "sselog")
6991    (set_attr "prefix_extra" "1")
6992    (set_attr "length_immediate" "1")
6993    (set_attr "prefix" "maybe_vex")
6994    (set_attr "mode" "TI")])
6995
6996 (define_insn "*sse2_pextrw_<mode>"
6997   [(set (match_operand:SWI48 0 "register_operand" "=r")
6998         (zero_extend:SWI48
6999           (vec_select:HI
7000             (match_operand:V8HI 1 "register_operand" "x")
7001             (parallel [(match_operand:SI 2 "const_0_to_7_operand" "n")]))))]
7002   "TARGET_SSE2"
7003   "%vpextrw\t{%2, %1, %k0|%k0, %1, %2}"
7004   [(set_attr "type" "sselog")
7005    (set_attr "prefix_data16" "1")
7006    (set_attr "length_immediate" "1")
7007    (set_attr "prefix" "maybe_vex")
7008    (set_attr "mode" "TI")])
7009
7010 (define_insn "*sse4_1_pextrw_memory"
7011   [(set (match_operand:HI 0 "memory_operand" "=m")
7012         (vec_select:HI
7013           (match_operand:V8HI 1 "register_operand" "x")
7014           (parallel [(match_operand:SI 2 "const_0_to_7_operand" "n")])))]
7015   "TARGET_SSE4_1"
7016   "%vpextrw\t{%2, %1, %0|%0, %1, %2}"
7017   [(set_attr "type" "sselog")
7018    (set_attr "prefix_extra" "1")
7019    (set_attr "length_immediate" "1")
7020    (set_attr "prefix" "maybe_vex")
7021    (set_attr "mode" "TI")])
7022
7023 (define_insn "*sse4_1_pextrd"
7024   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
7025         (vec_select:SI
7026           (match_operand:V4SI 1 "register_operand" "x")
7027           (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n")])))]
7028   "TARGET_SSE4_1"
7029   "%vpextrd\t{%2, %1, %0|%0, %1, %2}"
7030   [(set_attr "type" "sselog")
7031    (set_attr "prefix_extra" "1")
7032    (set_attr "length_immediate" "1")
7033    (set_attr "prefix" "maybe_vex")
7034    (set_attr "mode" "TI")])
7035
7036 (define_insn "*sse4_1_pextrd_zext"
7037   [(set (match_operand:DI 0 "register_operand" "=r")
7038         (zero_extend:DI
7039           (vec_select:SI
7040             (match_operand:V4SI 1 "register_operand" "x")
7041             (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n")]))))]
7042   "TARGET_64BIT && TARGET_SSE4_1"
7043   "%vpextrd\t{%2, %1, %k0|%k0, %1, %2}"
7044   [(set_attr "type" "sselog")
7045    (set_attr "prefix_extra" "1")
7046    (set_attr "length_immediate" "1")
7047    (set_attr "prefix" "maybe_vex")
7048    (set_attr "mode" "TI")])
7049
7050 ;; It must come before *vec_extractv2di_1_rex64 since it is preferred.
7051 (define_insn "*sse4_1_pextrq"
7052   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
7053         (vec_select:DI
7054           (match_operand:V2DI 1 "register_operand" "x")
7055           (parallel [(match_operand:SI 2 "const_0_to_1_operand" "n")])))]
7056   "TARGET_SSE4_1 && TARGET_64BIT"
7057   "%vpextrq\t{%2, %1, %0|%0, %1, %2}"
7058   [(set_attr "type" "sselog")
7059    (set_attr "prefix_rex" "1")
7060    (set_attr "prefix_extra" "1")
7061    (set_attr "length_immediate" "1")
7062    (set_attr "prefix" "maybe_vex")
7063    (set_attr "mode" "TI")])
7064
7065 (define_expand "avx2_pshufdv3"
7066   [(match_operand:V8SI 0 "register_operand" "")
7067    (match_operand:V8SI 1 "nonimmediate_operand" "")
7068    (match_operand:SI 2 "const_0_to_255_operand" "")]
7069   "TARGET_AVX2"
7070 {
7071   int mask = INTVAL (operands[2]);
7072   emit_insn (gen_avx2_pshufd_1 (operands[0], operands[1],
7073                                 GEN_INT ((mask >> 0) & 3),
7074                                 GEN_INT ((mask >> 2) & 3),
7075                                 GEN_INT ((mask >> 4) & 3),
7076                                 GEN_INT ((mask >> 6) & 3),
7077                                 GEN_INT (((mask >> 0) & 3) + 4),
7078                                 GEN_INT (((mask >> 2) & 3) + 4),
7079                                 GEN_INT (((mask >> 4) & 3) + 4),
7080                                 GEN_INT (((mask >> 6) & 3) + 4)));
7081   DONE;
7082 })
7083
7084 (define_insn "avx2_pshufd_1"
7085   [(set (match_operand:V8SI 0 "register_operand" "=x")
7086         (vec_select:V8SI
7087           (match_operand:V8SI 1 "nonimmediate_operand" "xm")
7088           (parallel [(match_operand 2 "const_0_to_3_operand" "")
7089                      (match_operand 3 "const_0_to_3_operand" "")
7090                      (match_operand 4 "const_0_to_3_operand" "")
7091                      (match_operand 5 "const_0_to_3_operand" "")
7092                      (match_operand 6 "const_4_to_7_operand" "")
7093                      (match_operand 7 "const_4_to_7_operand" "")
7094                      (match_operand 8 "const_4_to_7_operand" "")
7095                      (match_operand 9 "const_4_to_7_operand" "")])))]
7096   "TARGET_AVX2
7097    && INTVAL (operands[2]) + 4 == INTVAL (operands[6])
7098    && INTVAL (operands[3]) + 4 == INTVAL (operands[7])
7099    && INTVAL (operands[4]) + 4 == INTVAL (operands[8])
7100    && INTVAL (operands[5]) + 4 == INTVAL (operands[9])"
7101 {
7102   int mask = 0;
7103   mask |= INTVAL (operands[2]) << 0;
7104   mask |= INTVAL (operands[3]) << 2;
7105   mask |= INTVAL (operands[4]) << 4;
7106   mask |= INTVAL (operands[5]) << 6;
7107   operands[2] = GEN_INT (mask);
7108
7109   return "vpshufd\t{%2, %1, %0|%0, %1, %2}";
7110 }
7111   [(set_attr "type" "sselog1")
7112    (set_attr "prefix" "vex")
7113    (set_attr "length_immediate" "1")
7114    (set_attr "mode" "OI")])
7115
7116 (define_expand "sse2_pshufd"
7117   [(match_operand:V4SI 0 "register_operand" "")
7118    (match_operand:V4SI 1 "nonimmediate_operand" "")
7119    (match_operand:SI 2 "const_int_operand" "")]
7120   "TARGET_SSE2"
7121 {
7122   int mask = INTVAL (operands[2]);
7123   emit_insn (gen_sse2_pshufd_1 (operands[0], operands[1],
7124                                 GEN_INT ((mask >> 0) & 3),
7125                                 GEN_INT ((mask >> 2) & 3),
7126                                 GEN_INT ((mask >> 4) & 3),
7127                                 GEN_INT ((mask >> 6) & 3)));
7128   DONE;
7129 })
7130
7131 (define_insn "sse2_pshufd_1"
7132   [(set (match_operand:V4SI 0 "register_operand" "=x")
7133         (vec_select:V4SI
7134           (match_operand:V4SI 1 "nonimmediate_operand" "xm")
7135           (parallel [(match_operand 2 "const_0_to_3_operand" "")
7136                      (match_operand 3 "const_0_to_3_operand" "")
7137                      (match_operand 4 "const_0_to_3_operand" "")
7138                      (match_operand 5 "const_0_to_3_operand" "")])))]
7139   "TARGET_SSE2"
7140 {
7141   int mask = 0;
7142   mask |= INTVAL (operands[2]) << 0;
7143   mask |= INTVAL (operands[3]) << 2;
7144   mask |= INTVAL (operands[4]) << 4;
7145   mask |= INTVAL (operands[5]) << 6;
7146   operands[2] = GEN_INT (mask);
7147
7148   return "%vpshufd\t{%2, %1, %0|%0, %1, %2}";
7149 }
7150   [(set_attr "type" "sselog1")
7151    (set_attr "prefix_data16" "1")
7152    (set_attr "prefix" "maybe_vex")
7153    (set_attr "length_immediate" "1")
7154    (set_attr "mode" "TI")])
7155
7156 (define_expand "avx2_pshuflwv3"
7157   [(match_operand:V16HI 0 "register_operand" "")
7158    (match_operand:V16HI 1 "nonimmediate_operand" "")
7159    (match_operand:SI 2 "const_0_to_255_operand" "")]
7160   "TARGET_AVX2"
7161 {
7162   int mask = INTVAL (operands[2]);
7163   emit_insn (gen_avx2_pshuflw_1 (operands[0], operands[1],
7164                                  GEN_INT ((mask >> 0) & 3),
7165                                  GEN_INT ((mask >> 2) & 3),
7166                                  GEN_INT ((mask >> 4) & 3),
7167                                  GEN_INT ((mask >> 6) & 3),
7168                                  GEN_INT (((mask >> 0) & 3) + 8),
7169                                  GEN_INT (((mask >> 2) & 3) + 8),
7170                                  GEN_INT (((mask >> 4) & 3) + 8),
7171                                  GEN_INT (((mask >> 6) & 3) + 8)));
7172   DONE;
7173 })
7174
7175 (define_insn "avx2_pshuflw_1"
7176   [(set (match_operand:V16HI 0 "register_operand" "=x")
7177         (vec_select:V16HI
7178           (match_operand:V16HI 1 "nonimmediate_operand" "xm")
7179           (parallel [(match_operand 2 "const_0_to_3_operand" "")
7180                      (match_operand 3 "const_0_to_3_operand" "")
7181                      (match_operand 4 "const_0_to_3_operand" "")
7182                      (match_operand 5 "const_0_to_3_operand" "")
7183                      (const_int 4)
7184                      (const_int 5)
7185                      (const_int 6)
7186                      (const_int 7)
7187                      (match_operand 6 "const_8_to_11_operand" "")
7188                      (match_operand 7 "const_8_to_11_operand" "")
7189                      (match_operand 8 "const_8_to_11_operand" "")
7190                      (match_operand 9 "const_8_to_11_operand" "")
7191                      (const_int 12)
7192                      (const_int 13)
7193                      (const_int 14)
7194                      (const_int 15)])))]
7195   "TARGET_AVX2
7196    && INTVAL (operands[2]) + 8 == INTVAL (operands[6])
7197    && INTVAL (operands[3]) + 8 == INTVAL (operands[7])
7198    && INTVAL (operands[4]) + 8 == INTVAL (operands[8])
7199    && INTVAL (operands[5]) + 8 == INTVAL (operands[9])"
7200 {
7201   int mask = 0;
7202   mask |= INTVAL (operands[2]) << 0;
7203   mask |= INTVAL (operands[3]) << 2;
7204   mask |= INTVAL (operands[4]) << 4;
7205   mask |= INTVAL (operands[5]) << 6;
7206   operands[2] = GEN_INT (mask);
7207
7208   return "vpshuflw\t{%2, %1, %0|%0, %1, %2}";
7209 }
7210   [(set_attr "type" "sselog")
7211    (set_attr "prefix" "vex")
7212    (set_attr "length_immediate" "1")
7213    (set_attr "mode" "OI")])
7214
7215 (define_expand "sse2_pshuflw"
7216   [(match_operand:V8HI 0 "register_operand" "")
7217    (match_operand:V8HI 1 "nonimmediate_operand" "")
7218    (match_operand:SI 2 "const_int_operand" "")]
7219   "TARGET_SSE2"
7220 {
7221   int mask = INTVAL (operands[2]);
7222   emit_insn (gen_sse2_pshuflw_1 (operands[0], operands[1],
7223                                  GEN_INT ((mask >> 0) & 3),
7224                                  GEN_INT ((mask >> 2) & 3),
7225                                  GEN_INT ((mask >> 4) & 3),
7226                                  GEN_INT ((mask >> 6) & 3)));
7227   DONE;
7228 })
7229
7230 (define_insn "sse2_pshuflw_1"
7231   [(set (match_operand:V8HI 0 "register_operand" "=x")
7232         (vec_select:V8HI
7233           (match_operand:V8HI 1 "nonimmediate_operand" "xm")
7234           (parallel [(match_operand 2 "const_0_to_3_operand" "")
7235                      (match_operand 3 "const_0_to_3_operand" "")
7236                      (match_operand 4 "const_0_to_3_operand" "")
7237                      (match_operand 5 "const_0_to_3_operand" "")
7238                      (const_int 4)
7239                      (const_int 5)
7240                      (const_int 6)
7241                      (const_int 7)])))]
7242   "TARGET_SSE2"
7243 {
7244   int mask = 0;
7245   mask |= INTVAL (operands[2]) << 0;
7246   mask |= INTVAL (operands[3]) << 2;
7247   mask |= INTVAL (operands[4]) << 4;
7248   mask |= INTVAL (operands[5]) << 6;
7249   operands[2] = GEN_INT (mask);
7250
7251   return "%vpshuflw\t{%2, %1, %0|%0, %1, %2}";
7252 }
7253   [(set_attr "type" "sselog")
7254    (set_attr "prefix_data16" "0")
7255    (set_attr "prefix_rep" "1")
7256    (set_attr "prefix" "maybe_vex")
7257    (set_attr "length_immediate" "1")
7258    (set_attr "mode" "TI")])
7259
7260 (define_expand "avx2_pshufhwv3"
7261   [(match_operand:V16HI 0 "register_operand" "")
7262    (match_operand:V16HI 1 "nonimmediate_operand" "")
7263    (match_operand:SI 2 "const_0_to_255_operand" "")]
7264   "TARGET_AVX2"
7265 {
7266   int mask = INTVAL (operands[2]);
7267   emit_insn (gen_avx2_pshufhw_1 (operands[0], operands[1],
7268                                  GEN_INT (((mask >> 0) & 3) + 4),
7269                                  GEN_INT (((mask >> 2) & 3) + 4),
7270                                  GEN_INT (((mask >> 4) & 3) + 4),
7271                                  GEN_INT (((mask >> 6) & 3) + 4),
7272                                  GEN_INT (((mask >> 0) & 3) + 12),
7273                                  GEN_INT (((mask >> 2) & 3) + 12),
7274                                  GEN_INT (((mask >> 4) & 3) + 12),
7275                                  GEN_INT (((mask >> 6) & 3) + 12)));
7276   DONE;
7277 })
7278
7279 (define_insn "avx2_pshufhw_1"
7280   [(set (match_operand:V16HI 0 "register_operand" "=x")
7281         (vec_select:V16HI
7282           (match_operand:V16HI 1 "nonimmediate_operand" "xm")
7283           (parallel [(const_int 0)
7284                      (const_int 1)
7285                      (const_int 2)
7286                      (const_int 3)
7287                      (match_operand 2 "const_4_to_7_operand" "")
7288                      (match_operand 3 "const_4_to_7_operand" "")
7289                      (match_operand 4 "const_4_to_7_operand" "")
7290                      (match_operand 5 "const_4_to_7_operand" "")
7291                      (const_int 8)
7292                      (const_int 9)
7293                      (const_int 10)
7294                      (const_int 11)
7295                      (match_operand 6 "const_12_to_15_operand" "")
7296                      (match_operand 7 "const_12_to_15_operand" "")
7297                      (match_operand 8 "const_12_to_15_operand" "")
7298                      (match_operand 9 "const_12_to_15_operand" "")])))]
7299   "TARGET_AVX2
7300    && INTVAL (operands[2]) + 8 == INTVAL (operands[6])
7301    && INTVAL (operands[3]) + 8 == INTVAL (operands[7])
7302    && INTVAL (operands[4]) + 8 == INTVAL (operands[8])
7303    && INTVAL (operands[5]) + 8 == INTVAL (operands[9])"
7304 {
7305   int mask = 0;
7306   mask |= (INTVAL (operands[2]) - 4) << 0;
7307   mask |= (INTVAL (operands[3]) - 4) << 2;
7308   mask |= (INTVAL (operands[4]) - 4) << 4;
7309   mask |= (INTVAL (operands[5]) - 4) << 6;
7310   operands[2] = GEN_INT (mask);
7311
7312   return "vpshufhw\t{%2, %1, %0|%0, %1, %2}";
7313 }
7314   [(set_attr "type" "sselog")
7315    (set_attr "prefix" "vex")
7316    (set_attr "length_immediate" "1")
7317    (set_attr "mode" "OI")])
7318
7319 (define_expand "sse2_pshufhw"
7320   [(match_operand:V8HI 0 "register_operand" "")
7321    (match_operand:V8HI 1 "nonimmediate_operand" "")
7322    (match_operand:SI 2 "const_int_operand" "")]
7323   "TARGET_SSE2"
7324 {
7325   int mask = INTVAL (operands[2]);
7326   emit_insn (gen_sse2_pshufhw_1 (operands[0], operands[1],
7327                                  GEN_INT (((mask >> 0) & 3) + 4),
7328                                  GEN_INT (((mask >> 2) & 3) + 4),
7329                                  GEN_INT (((mask >> 4) & 3) + 4),
7330                                  GEN_INT (((mask >> 6) & 3) + 4)));
7331   DONE;
7332 })
7333
7334 (define_insn "sse2_pshufhw_1"
7335   [(set (match_operand:V8HI 0 "register_operand" "=x")
7336         (vec_select:V8HI
7337           (match_operand:V8HI 1 "nonimmediate_operand" "xm")
7338           (parallel [(const_int 0)
7339                      (const_int 1)
7340                      (const_int 2)
7341                      (const_int 3)
7342                      (match_operand 2 "const_4_to_7_operand" "")
7343                      (match_operand 3 "const_4_to_7_operand" "")
7344                      (match_operand 4 "const_4_to_7_operand" "")
7345                      (match_operand 5 "const_4_to_7_operand" "")])))]
7346   "TARGET_SSE2"
7347 {
7348   int mask = 0;
7349   mask |= (INTVAL (operands[2]) - 4) << 0;
7350   mask |= (INTVAL (operands[3]) - 4) << 2;
7351   mask |= (INTVAL (operands[4]) - 4) << 4;
7352   mask |= (INTVAL (operands[5]) - 4) << 6;
7353   operands[2] = GEN_INT (mask);
7354
7355   return "%vpshufhw\t{%2, %1, %0|%0, %1, %2}";
7356 }
7357   [(set_attr "type" "sselog")
7358    (set_attr "prefix_rep" "1")
7359    (set_attr "prefix_data16" "0")
7360    (set_attr "prefix" "maybe_vex")
7361    (set_attr "length_immediate" "1")
7362    (set_attr "mode" "TI")])
7363
7364 (define_expand "sse2_loadd"
7365   [(set (match_operand:V4SI 0 "register_operand" "")
7366         (vec_merge:V4SI
7367           (vec_duplicate:V4SI
7368             (match_operand:SI 1 "nonimmediate_operand" ""))
7369           (match_dup 2)
7370           (const_int 1)))]
7371   "TARGET_SSE"
7372   "operands[2] = CONST0_RTX (V4SImode);")
7373
7374 (define_insn "sse2_loadld"
7375   [(set (match_operand:V4SI 0 "register_operand"       "=x,Yi,x,x,x")
7376         (vec_merge:V4SI
7377           (vec_duplicate:V4SI
7378             (match_operand:SI 2 "nonimmediate_operand" "m ,r ,m,x,x"))
7379           (match_operand:V4SI 1 "reg_or_0_operand"     "C ,C ,C,0,x")
7380           (const_int 1)))]
7381   "TARGET_SSE"
7382   "@
7383    %vmovd\t{%2, %0|%0, %2}
7384    %vmovd\t{%2, %0|%0, %2}
7385    movss\t{%2, %0|%0, %2}
7386    movss\t{%2, %0|%0, %2}
7387    vmovss\t{%2, %1, %0|%0, %1, %2}"
7388   [(set_attr "isa" "sse2,*,noavx,noavx,avx")
7389    (set_attr "type" "ssemov")
7390    (set_attr "prefix" "maybe_vex,maybe_vex,orig,orig,vex")
7391    (set_attr "mode" "TI,TI,V4SF,SF,SF")])
7392
7393 (define_insn_and_split "sse2_stored"
7394   [(set (match_operand:SI 0 "nonimmediate_operand" "=xm,r")
7395         (vec_select:SI
7396           (match_operand:V4SI 1 "register_operand" "x,Yi")
7397           (parallel [(const_int 0)])))]
7398   "TARGET_SSE"
7399   "#"
7400   "&& reload_completed
7401    && (TARGET_INTER_UNIT_MOVES
7402        || MEM_P (operands [0])
7403        || !GENERAL_REGNO_P (true_regnum (operands [0])))"
7404   [(set (match_dup 0) (match_dup 1))]
7405   "operands[1] = gen_rtx_REG (SImode, REGNO (operands[1]));")
7406
7407 (define_insn_and_split "*vec_ext_v4si_mem"
7408   [(set (match_operand:SI 0 "register_operand" "=r")
7409         (vec_select:SI
7410           (match_operand:V4SI 1 "memory_operand" "o")
7411           (parallel [(match_operand 2 "const_0_to_3_operand" "")])))]
7412   ""
7413   "#"
7414   "reload_completed"
7415   [(const_int 0)]
7416 {
7417   int i = INTVAL (operands[2]);
7418
7419   emit_move_insn (operands[0], adjust_address (operands[1], SImode, i*4));
7420   DONE;
7421 })
7422
7423 (define_expand "sse_storeq"
7424   [(set (match_operand:DI 0 "nonimmediate_operand" "")
7425         (vec_select:DI
7426           (match_operand:V2DI 1 "register_operand" "")
7427           (parallel [(const_int 0)])))]
7428   "TARGET_SSE")
7429
7430 (define_insn "*sse2_storeq_rex64"
7431   [(set (match_operand:DI 0 "nonimmediate_operand" "=xm,*r,r")
7432         (vec_select:DI
7433           (match_operand:V2DI 1 "nonimmediate_operand" "x,Yi,o")
7434           (parallel [(const_int 0)])))]
7435   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7436   "@
7437    #
7438    #
7439    mov{q}\t{%1, %0|%0, %1}"
7440   [(set_attr "type" "*,*,imov")
7441    (set_attr "mode" "*,*,DI")])
7442
7443 (define_insn "*sse2_storeq"
7444   [(set (match_operand:DI 0 "nonimmediate_operand" "=xm")
7445         (vec_select:DI
7446           (match_operand:V2DI 1 "register_operand" "x")
7447           (parallel [(const_int 0)])))]
7448   "TARGET_SSE"
7449   "#")
7450
7451 (define_split
7452   [(set (match_operand:DI 0 "nonimmediate_operand" "")
7453         (vec_select:DI
7454           (match_operand:V2DI 1 "register_operand" "")
7455           (parallel [(const_int 0)])))]
7456   "TARGET_SSE
7457    && reload_completed
7458    && (TARGET_INTER_UNIT_MOVES
7459        || MEM_P (operands [0])
7460        || !GENERAL_REGNO_P (true_regnum (operands [0])))"
7461   [(set (match_dup 0) (match_dup 1))]
7462   "operands[1] = gen_rtx_REG (DImode, REGNO (operands[1]));")
7463
7464 (define_insn "*vec_extractv2di_1_rex64"
7465   [(set (match_operand:DI 0 "nonimmediate_operand"     "=m,x,x,x,r")
7466         (vec_select:DI
7467           (match_operand:V2DI 1 "nonimmediate_operand" " x,0,x,o,o")
7468           (parallel [(const_int 1)])))]
7469   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7470   "@
7471    %vmovhps\t{%1, %0|%0, %1}
7472    psrldq\t{$8, %0|%0, 8}
7473    vpsrldq\t{$8, %1, %0|%0, %1, 8}
7474    %vmovq\t{%H1, %0|%0, %H1}
7475    mov{q}\t{%H1, %0|%0, %H1}"
7476   [(set_attr "isa" "*,noavx,avx,*,*")
7477    (set_attr "type" "ssemov,sseishft1,sseishft1,ssemov,imov")
7478    (set_attr "length_immediate" "*,1,1,*,*")
7479    (set_attr "memory" "*,none,none,*,*")
7480    (set_attr "prefix" "maybe_vex,orig,vex,maybe_vex,orig")
7481    (set_attr "mode" "V2SF,TI,TI,TI,DI")])
7482
7483 (define_insn "*vec_extractv2di_1"
7484   [(set (match_operand:DI 0 "nonimmediate_operand"     "=m,x,x,x,x,x")
7485         (vec_select:DI
7486           (match_operand:V2DI 1 "nonimmediate_operand" " x,0,x,o,x,o")
7487           (parallel [(const_int 1)])))]
7488   "!TARGET_64BIT && TARGET_SSE
7489    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7490   "@
7491    %vmovhps\t{%1, %0|%0, %1}
7492    psrldq\t{$8, %0|%0, 8}
7493    vpsrldq\t{$8, %1, %0|%0, %1, 8}
7494    %vmovq\t{%H1, %0|%0, %H1}
7495    movhlps\t{%1, %0|%0, %1}
7496    movlps\t{%H1, %0|%0, %H1}"
7497   [(set_attr "isa" "*,sse2_noavx,avx,sse2,noavx,noavx")
7498    (set_attr "type" "ssemov,sseishft1,sseishft1,ssemov,ssemov,ssemov")
7499    (set_attr "length_immediate" "*,1,1,*,*,*")
7500    (set_attr "memory" "*,none,none,*,*,*")
7501    (set_attr "prefix" "maybe_vex,orig,vex,maybe_vex,orig,orig")
7502    (set_attr "mode" "V2SF,TI,TI,TI,V4SF,V2SF")])
7503
7504 (define_insn "*vec_dupv4si"
7505   [(set (match_operand:V4SI 0 "register_operand"     "=x,x,x")
7506         (vec_duplicate:V4SI
7507           (match_operand:SI 1 "nonimmediate_operand" " x,m,0")))]
7508   "TARGET_SSE"
7509   "@
7510    %vpshufd\t{$0, %1, %0|%0, %1, 0}
7511    vbroadcastss\t{%1, %0|%0, %1}
7512    shufps\t{$0, %0, %0|%0, %0, 0}"
7513   [(set_attr "isa" "sse2,avx,noavx")
7514    (set_attr "type" "sselog1,ssemov,sselog1")
7515    (set_attr "length_immediate" "1,0,1")
7516    (set_attr "prefix_extra" "0,1,*")
7517    (set_attr "prefix" "maybe_vex,vex,orig")
7518    (set_attr "mode" "TI,V4SF,V4SF")])
7519
7520 (define_insn "*vec_dupv2di"
7521   [(set (match_operand:V2DI 0 "register_operand"     "=x,x,x,x")
7522         (vec_duplicate:V2DI
7523           (match_operand:DI 1 "nonimmediate_operand" " 0,x,m,0")))]
7524   "TARGET_SSE"
7525   "@
7526    punpcklqdq\t%0, %0
7527    vpunpcklqdq\t{%d1, %0|%0, %d1}
7528    %vmovddup\t{%1, %0|%0, %1}
7529    movlhps\t%0, %0"
7530   [(set_attr "isa" "sse2_noavx,avx,sse3,noavx")
7531    (set_attr "type" "sselog1,sselog1,sselog1,ssemov")
7532    (set_attr "prefix" "orig,vex,maybe_vex,orig")
7533    (set_attr "mode" "TI,TI,DF,V4SF")])
7534
7535 (define_insn "*vec_concatv2si_sse4_1"
7536   [(set (match_operand:V2SI 0 "register_operand"     "=x, x,x,x, x, *y,*y")
7537         (vec_concat:V2SI
7538           (match_operand:SI 1 "nonimmediate_operand" " 0, x,0,x,rm,  0,rm")
7539           (match_operand:SI 2 "vector_move_operand"  "rm,rm,x,x, C,*ym, C")))]
7540   "TARGET_SSE4_1"
7541   "@
7542    pinsrd\t{$1, %2, %0|%0, %2, 1}
7543    vpinsrd\t{$1, %2, %1, %0|%0, %1, %2, 1}
7544    punpckldq\t{%2, %0|%0, %2}
7545    vpunpckldq\t{%2, %1, %0|%0, %1, %2}
7546    %vmovd\t{%1, %0|%0, %1}
7547    punpckldq\t{%2, %0|%0, %2}
7548    movd\t{%1, %0|%0, %1}"
7549   [(set_attr "isa" "noavx,avx,noavx,avx,*,*,*")
7550    (set_attr "type" "sselog,sselog,sselog,sselog,ssemov,mmxcvt,mmxmov")
7551    (set_attr "prefix_extra" "1,1,*,*,*,*,*")
7552    (set_attr "length_immediate" "1,1,*,*,*,*,*")
7553    (set_attr "prefix" "orig,vex,orig,vex,maybe_vex,orig,orig")
7554    (set_attr "mode" "TI,TI,TI,TI,TI,DI,DI")])
7555
7556 ;; ??? In theory we can match memory for the MMX alternative, but allowing
7557 ;; nonimmediate_operand for operand 2 and *not* allowing memory for the SSE
7558 ;; alternatives pretty much forces the MMX alternative to be chosen.
7559 (define_insn "*vec_concatv2si_sse2"
7560   [(set (match_operand:V2SI 0 "register_operand"     "=x,x ,*y,*y")
7561         (vec_concat:V2SI
7562           (match_operand:SI 1 "nonimmediate_operand" " 0,rm, 0,rm")
7563           (match_operand:SI 2 "reg_or_0_operand"     " x,C ,*y, C")))]
7564   "TARGET_SSE2"
7565   "@
7566    punpckldq\t{%2, %0|%0, %2}
7567    movd\t{%1, %0|%0, %1}
7568    punpckldq\t{%2, %0|%0, %2}
7569    movd\t{%1, %0|%0, %1}"
7570   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
7571    (set_attr "mode" "TI,TI,DI,DI")])
7572
7573 (define_insn "*vec_concatv2si_sse"
7574   [(set (match_operand:V2SI 0 "register_operand"     "=x,x,*y,*y")
7575         (vec_concat:V2SI
7576           (match_operand:SI 1 "nonimmediate_operand" " 0,m, 0,*rm")
7577           (match_operand:SI 2 "reg_or_0_operand"     " x,C,*y,C")))]
7578   "TARGET_SSE"
7579   "@
7580    unpcklps\t{%2, %0|%0, %2}
7581    movss\t{%1, %0|%0, %1}
7582    punpckldq\t{%2, %0|%0, %2}
7583    movd\t{%1, %0|%0, %1}"
7584   [(set_attr "type" "sselog,ssemov,mmxcvt,mmxmov")
7585    (set_attr "mode" "V4SF,V4SF,DI,DI")])
7586
7587 (define_insn "*vec_concatv4si"
7588   [(set (match_operand:V4SI 0 "register_operand"       "=x,x,x,x,x")
7589         (vec_concat:V4SI
7590           (match_operand:V2SI 1 "register_operand"     " 0,x,0,0,x")
7591           (match_operand:V2SI 2 "nonimmediate_operand" " x,x,x,m,m")))]
7592   "TARGET_SSE"
7593   "@
7594    punpcklqdq\t{%2, %0|%0, %2}
7595    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7596    movlhps\t{%2, %0|%0, %2}
7597    movhps\t{%2, %0|%0, %2}
7598    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7599   [(set_attr "isa" "sse2_noavx,avx,noavx,noavx,avx")
7600    (set_attr "type" "sselog,sselog,ssemov,ssemov,ssemov")
7601    (set_attr "prefix" "orig,vex,orig,orig,vex")
7602    (set_attr "mode" "TI,TI,V4SF,V2SF,V2SF")])
7603
7604 ;; movd instead of movq is required to handle broken assemblers.
7605 (define_insn "*vec_concatv2di_rex64"
7606   [(set (match_operand:V2DI 0 "register_operand"
7607           "=x,x ,x ,Yi,!x,x,x,x,x")
7608         (vec_concat:V2DI
7609           (match_operand:DI 1 "nonimmediate_operand"
7610           " 0,x ,xm,r ,*y,0,x,0,x")
7611           (match_operand:DI 2 "vector_move_operand"
7612           "rm,rm,C ,C ,C ,x,x,m,m")))]
7613   "TARGET_64BIT"
7614   "@
7615    pinsrq\t{$1, %2, %0|%0, %2, 1}
7616    vpinsrq\t{$1, %2, %1, %0|%0, %1, %2, 1}
7617    %vmovq\t{%1, %0|%0, %1}
7618    %vmovd\t{%1, %0|%0, %1}
7619    movq2dq\t{%1, %0|%0, %1}
7620    punpcklqdq\t{%2, %0|%0, %2}
7621    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7622    movhps\t{%2, %0|%0, %2}
7623    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7624   [(set_attr "isa" "sse4_noavx,avx,*,*,*,noavx,avx,noavx,avx")
7625    (set (attr "type")
7626      (if_then_else
7627        (eq_attr "alternative" "0,1,5,6")
7628        (const_string "sselog")
7629        (const_string "ssemov")))
7630    (set (attr "prefix_rex")
7631      (if_then_else
7632        (and (eq_attr "alternative" "0,3")
7633             (not (match_test "TARGET_AVX")))
7634        (const_string "1")
7635        (const_string "*")))
7636    (set_attr "prefix_extra" "1,1,*,*,*,*,*,*,*")
7637    (set_attr "length_immediate" "1,1,*,*,*,*,*,*,*")
7638    (set_attr "prefix" "orig,vex,maybe_vex,maybe_vex,orig,orig,vex,orig,vex")
7639    (set_attr "mode" "TI,TI,TI,TI,TI,TI,TI,V2SF,V2SF")])
7640
7641 (define_insn "vec_concatv2di"
7642   [(set (match_operand:V2DI 0 "register_operand"     "=x,?x,x,x,x,x,x")
7643         (vec_concat:V2DI
7644           (match_operand:DI 1 "nonimmediate_operand" "xm,*y,0,x,0,0,x")
7645           (match_operand:DI 2 "vector_move_operand"  " C, C,x,x,x,m,m")))]
7646   "!TARGET_64BIT && TARGET_SSE"
7647   "@
7648    %vmovq\t{%1, %0|%0, %1}
7649    movq2dq\t{%1, %0|%0, %1}
7650    punpcklqdq\t{%2, %0|%0, %2}
7651    vpunpcklqdq\t{%2, %1, %0|%0, %1, %2}
7652    movlhps\t{%2, %0|%0, %2}
7653    movhps\t{%2, %0|%0, %2}
7654    vmovhps\t{%2, %1, %0|%0, %1, %2}"
7655   [(set_attr "isa" "sse2,sse2,sse2_noavx,avx,noavx,noavx,avx")
7656    (set_attr "type" "ssemov,ssemov,sselog,sselog,ssemov,ssemov,ssemov")
7657    (set_attr "prefix" "maybe_vex,orig,orig,vex,orig,orig,vex")
7658    (set_attr "mode" "TI,TI,TI,TI,V4SF,V2SF,V2SF")])
7659
7660 (define_expand "vec_unpacks_lo_<mode>"
7661   [(match_operand:<sseunpackmode> 0 "register_operand" "")
7662    (match_operand:VI124_AVX2 1 "register_operand" "")]
7663   "TARGET_SSE2"
7664   "ix86_expand_sse_unpack (operands, false, false); DONE;")
7665
7666 (define_expand "vec_unpacks_hi_<mode>"
7667   [(match_operand:<sseunpackmode> 0 "register_operand" "")
7668    (match_operand:VI124_AVX2 1 "register_operand" "")]
7669   "TARGET_SSE2"
7670   "ix86_expand_sse_unpack (operands, false, true); DONE;")
7671
7672 (define_expand "vec_unpacku_lo_<mode>"
7673   [(match_operand:<sseunpackmode> 0 "register_operand" "")
7674    (match_operand:VI124_AVX2 1 "register_operand" "")]
7675   "TARGET_SSE2"
7676   "ix86_expand_sse_unpack (operands, true, false); DONE;")
7677
7678 (define_expand "vec_unpacku_hi_<mode>"
7679   [(match_operand:<sseunpackmode> 0 "register_operand" "")
7680    (match_operand:VI124_AVX2 1 "register_operand" "")]
7681   "TARGET_SSE2"
7682   "ix86_expand_sse_unpack (operands, true, true); DONE;")
7683
7684 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7685 ;;
7686 ;; Miscellaneous
7687 ;;
7688 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7689
7690 (define_expand "avx2_uavgv32qi3"
7691   [(set (match_operand:V32QI 0 "register_operand" "")
7692         (truncate:V32QI
7693           (lshiftrt:V32HI
7694             (plus:V32HI
7695               (plus:V32HI
7696                 (zero_extend:V32HI
7697                   (match_operand:V32QI 1 "nonimmediate_operand" ""))
7698                 (zero_extend:V32HI
7699                   (match_operand:V32QI 2 "nonimmediate_operand" "")))
7700               (const_vector:V32QI [(const_int 1) (const_int 1)
7701                                    (const_int 1) (const_int 1)
7702                                    (const_int 1) (const_int 1)
7703                                    (const_int 1) (const_int 1)
7704                                    (const_int 1) (const_int 1)
7705                                    (const_int 1) (const_int 1)
7706                                    (const_int 1) (const_int 1)
7707                                    (const_int 1) (const_int 1)
7708                                    (const_int 1) (const_int 1)
7709                                    (const_int 1) (const_int 1)
7710                                    (const_int 1) (const_int 1)
7711                                    (const_int 1) (const_int 1)
7712                                    (const_int 1) (const_int 1)
7713                                    (const_int 1) (const_int 1)
7714                                    (const_int 1) (const_int 1)
7715                                    (const_int 1) (const_int 1)]))
7716             (const_int 1))))]
7717   "TARGET_AVX2"
7718   "ix86_fixup_binary_operands_no_copy (PLUS, V32QImode, operands);")
7719
7720 (define_expand "sse2_uavgv16qi3"
7721   [(set (match_operand:V16QI 0 "register_operand" "")
7722         (truncate:V16QI
7723           (lshiftrt:V16HI
7724             (plus:V16HI
7725               (plus:V16HI
7726                 (zero_extend:V16HI
7727                   (match_operand:V16QI 1 "nonimmediate_operand" ""))
7728                 (zero_extend:V16HI
7729                   (match_operand:V16QI 2 "nonimmediate_operand" "")))
7730               (const_vector:V16QI [(const_int 1) (const_int 1)
7731                                    (const_int 1) (const_int 1)
7732                                    (const_int 1) (const_int 1)
7733                                    (const_int 1) (const_int 1)
7734                                    (const_int 1) (const_int 1)
7735                                    (const_int 1) (const_int 1)
7736                                    (const_int 1) (const_int 1)
7737                                    (const_int 1) (const_int 1)]))
7738             (const_int 1))))]
7739   "TARGET_SSE2"
7740   "ix86_fixup_binary_operands_no_copy (PLUS, V16QImode, operands);")
7741
7742 (define_insn "*avx2_uavgv32qi3"
7743   [(set (match_operand:V32QI 0 "register_operand" "=x")
7744         (truncate:V32QI
7745           (lshiftrt:V32HI
7746             (plus:V32HI
7747               (plus:V32HI
7748                 (zero_extend:V32HI
7749                   (match_operand:V32QI 1 "nonimmediate_operand" "%x"))
7750                 (zero_extend:V32HI
7751                   (match_operand:V32QI 2 "nonimmediate_operand" "xm")))
7752               (const_vector:V32QI [(const_int 1) (const_int 1)
7753                                    (const_int 1) (const_int 1)
7754                                    (const_int 1) (const_int 1)
7755                                    (const_int 1) (const_int 1)
7756                                    (const_int 1) (const_int 1)
7757                                    (const_int 1) (const_int 1)
7758                                    (const_int 1) (const_int 1)
7759                                    (const_int 1) (const_int 1)
7760                                    (const_int 1) (const_int 1)
7761                                    (const_int 1) (const_int 1)
7762                                    (const_int 1) (const_int 1)
7763                                    (const_int 1) (const_int 1)
7764                                    (const_int 1) (const_int 1)
7765                                    (const_int 1) (const_int 1)
7766                                    (const_int 1) (const_int 1)
7767                                    (const_int 1) (const_int 1)]))
7768             (const_int 1))))]
7769   "TARGET_AVX2 && ix86_binary_operator_ok (PLUS, V32QImode, operands)"
7770   "vpavgb\t{%2, %1, %0|%0, %1, %2}"
7771   [(set_attr "type" "sseiadd")
7772    (set_attr "prefix" "vex")
7773    (set_attr "mode" "OI")])
7774
7775 (define_insn "*sse2_uavgv16qi3"
7776   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
7777         (truncate:V16QI
7778           (lshiftrt:V16HI
7779             (plus:V16HI
7780               (plus:V16HI
7781                 (zero_extend:V16HI
7782                   (match_operand:V16QI 1 "nonimmediate_operand" "%0,x"))
7783                 (zero_extend:V16HI
7784                   (match_operand:V16QI 2 "nonimmediate_operand" "xm,xm")))
7785               (const_vector:V16QI [(const_int 1) (const_int 1)
7786                                    (const_int 1) (const_int 1)
7787                                    (const_int 1) (const_int 1)
7788                                    (const_int 1) (const_int 1)
7789                                    (const_int 1) (const_int 1)
7790                                    (const_int 1) (const_int 1)
7791                                    (const_int 1) (const_int 1)
7792                                    (const_int 1) (const_int 1)]))
7793             (const_int 1))))]
7794   "TARGET_SSE2 && ix86_binary_operator_ok (PLUS, V16QImode, operands)"
7795   "@
7796    pavgb\t{%2, %0|%0, %2}
7797    vpavgb\t{%2, %1, %0|%0, %1, %2}"
7798   [(set_attr "isa" "noavx,avx")
7799    (set_attr "type" "sseiadd")
7800    (set_attr "prefix_data16" "1,*")
7801    (set_attr "prefix" "orig,vex")
7802    (set_attr "mode" "TI")])
7803
7804 (define_expand "avx2_uavgv16hi3"
7805   [(set (match_operand:V16HI 0 "register_operand" "")
7806         (truncate:V16HI
7807           (lshiftrt:V16SI
7808             (plus:V16SI
7809               (plus:V16SI
7810                 (zero_extend:V16SI
7811                   (match_operand:V16HI 1 "nonimmediate_operand" ""))
7812                 (zero_extend:V16SI
7813                   (match_operand:V16HI 2 "nonimmediate_operand" "")))
7814               (const_vector:V16HI [(const_int 1) (const_int 1)
7815                                    (const_int 1) (const_int 1)
7816                                    (const_int 1) (const_int 1)
7817                                    (const_int 1) (const_int 1)
7818                                    (const_int 1) (const_int 1)
7819                                    (const_int 1) (const_int 1)
7820                                    (const_int 1) (const_int 1)
7821                                    (const_int 1) (const_int 1)]))
7822             (const_int 1))))]
7823   "TARGET_AVX2"
7824   "ix86_fixup_binary_operands_no_copy (PLUS, V16HImode, operands);")
7825
7826 (define_expand "sse2_uavgv8hi3"
7827   [(set (match_operand:V8HI 0 "register_operand" "")
7828         (truncate:V8HI
7829           (lshiftrt:V8SI
7830             (plus:V8SI
7831               (plus:V8SI
7832                 (zero_extend:V8SI
7833                   (match_operand:V8HI 1 "nonimmediate_operand" ""))
7834                 (zero_extend:V8SI
7835                   (match_operand:V8HI 2 "nonimmediate_operand" "")))
7836               (const_vector:V8HI [(const_int 1) (const_int 1)
7837                                   (const_int 1) (const_int 1)
7838                                   (const_int 1) (const_int 1)
7839                                   (const_int 1) (const_int 1)]))
7840             (const_int 1))))]
7841   "TARGET_SSE2"
7842   "ix86_fixup_binary_operands_no_copy (PLUS, V8HImode, operands);")
7843
7844 (define_insn "*avx2_uavgv16hi3"
7845   [(set (match_operand:V16HI 0 "register_operand" "=x")
7846         (truncate:V16HI
7847           (lshiftrt:V16SI
7848             (plus:V16SI
7849               (plus:V16SI
7850                 (zero_extend:V16SI
7851                   (match_operand:V16HI 1 "nonimmediate_operand" "%x"))
7852                 (zero_extend:V16SI
7853                   (match_operand:V16HI 2 "nonimmediate_operand" "xm")))
7854               (const_vector:V16HI [(const_int 1) (const_int 1)
7855                                    (const_int 1) (const_int 1)
7856                                    (const_int 1) (const_int 1)
7857                                    (const_int 1) (const_int 1)
7858                                    (const_int 1) (const_int 1)
7859                                    (const_int 1) (const_int 1)
7860                                    (const_int 1) (const_int 1)
7861                                    (const_int 1) (const_int 1)]))
7862             (const_int 1))))]
7863   "TARGET_AVX2 && ix86_binary_operator_ok (PLUS, V16HImode, operands)"
7864   "vpavgw\t{%2, %1, %0|%0, %1, %2}"
7865   [(set_attr "type" "sseiadd")
7866    (set_attr "prefix" "vex")
7867    (set_attr "mode" "OI")])
7868
7869 (define_insn "*sse2_uavgv8hi3"
7870   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
7871         (truncate:V8HI
7872           (lshiftrt:V8SI
7873             (plus:V8SI
7874               (plus:V8SI
7875                 (zero_extend:V8SI
7876                   (match_operand:V8HI 1 "nonimmediate_operand" "%0,x"))
7877                 (zero_extend:V8SI
7878                   (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")))
7879               (const_vector:V8HI [(const_int 1) (const_int 1)
7880                                   (const_int 1) (const_int 1)
7881                                   (const_int 1) (const_int 1)
7882                                   (const_int 1) (const_int 1)]))
7883             (const_int 1))))]
7884   "TARGET_SSE2 && ix86_binary_operator_ok (PLUS, V8HImode, operands)"
7885   "@
7886    pavgw\t{%2, %0|%0, %2}
7887    vpavgw\t{%2, %1, %0|%0, %1, %2}"
7888   [(set_attr "isa" "noavx,avx")
7889    (set_attr "type" "sseiadd")
7890    (set_attr "prefix_data16" "1,*")
7891    (set_attr "prefix" "orig,vex")
7892    (set_attr "mode" "TI")])
7893
7894 ;; The correct representation for this is absolutely enormous, and
7895 ;; surely not generally useful.
7896 (define_insn "<sse2_avx2>_psadbw"
7897   [(set (match_operand:VI8_AVX2 0 "register_operand" "=x,x")
7898         (unspec:VI8_AVX2 [(match_operand:<ssebytemode> 1 "register_operand" "0,x")
7899                           (match_operand:<ssebytemode> 2 "nonimmediate_operand" "xm,xm")]
7900                           UNSPEC_PSADBW))]
7901   "TARGET_SSE2"
7902   "@
7903    psadbw\t{%2, %0|%0, %2}
7904    vpsadbw\t{%2, %1, %0|%0, %1, %2}"
7905   [(set_attr "isa" "noavx,avx")
7906    (set_attr "type" "sseiadd")
7907    (set_attr "atom_unit" "simul")
7908    (set_attr "prefix_data16" "1,*")
7909    (set_attr "prefix" "orig,vex")
7910    (set_attr "mode" "<sseinsnmode>")])
7911
7912 (define_insn "<sse>_movmsk<ssemodesuffix><avxsizesuffix>"
7913   [(set (match_operand:SI 0 "register_operand" "=r")
7914         (unspec:SI
7915           [(match_operand:VF 1 "register_operand" "x")]
7916           UNSPEC_MOVMSK))]
7917   "TARGET_SSE"
7918   "%vmovmsk<ssemodesuffix>\t{%1, %0|%0, %1}"
7919   [(set_attr "type" "ssemov")
7920    (set_attr "prefix" "maybe_vex")
7921    (set_attr "mode" "<MODE>")])
7922
7923 (define_insn "avx2_pmovmskb"
7924   [(set (match_operand:SI 0 "register_operand" "=r")
7925         (unspec:SI [(match_operand:V32QI 1 "register_operand" "x")]
7926                    UNSPEC_MOVMSK))]
7927   "TARGET_AVX2"
7928   "vpmovmskb\t{%1, %0|%0, %1}"
7929   [(set_attr "type" "ssemov")
7930    (set_attr "prefix" "vex")
7931    (set_attr "mode" "DI")])
7932
7933 (define_insn "sse2_pmovmskb"
7934   [(set (match_operand:SI 0 "register_operand" "=r")
7935         (unspec:SI [(match_operand:V16QI 1 "register_operand" "x")]
7936                    UNSPEC_MOVMSK))]
7937   "TARGET_SSE2"
7938   "%vpmovmskb\t{%1, %0|%0, %1}"
7939   [(set_attr "type" "ssemov")
7940    (set_attr "prefix_data16" "1")
7941    (set_attr "prefix" "maybe_vex")
7942    (set_attr "mode" "SI")])
7943
7944 (define_expand "sse2_maskmovdqu"
7945   [(set (match_operand:V16QI 0 "memory_operand" "")
7946         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "")
7947                        (match_operand:V16QI 2 "register_operand" "")
7948                        (match_dup 0)]
7949                       UNSPEC_MASKMOV))]
7950   "TARGET_SSE2")
7951
7952 (define_insn "*sse2_maskmovdqu"
7953   [(set (mem:V16QI (match_operand:P 0 "register_operand" "D"))
7954         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
7955                        (match_operand:V16QI 2 "register_operand" "x")
7956                        (mem:V16QI (match_dup 0))]
7957                       UNSPEC_MASKMOV))]
7958   "TARGET_SSE2"
7959   "%vmaskmovdqu\t{%2, %1|%1, %2}"
7960   [(set_attr "type" "ssemov")
7961    (set_attr "prefix_data16" "1")
7962    ;; The implicit %rdi operand confuses default length_vex computation.
7963    (set (attr "length_vex")
7964      (symbol_ref ("3 + REX_SSE_REGNO_P (REGNO (operands[2]))")))
7965    (set_attr "prefix" "maybe_vex")
7966    (set_attr "mode" "TI")])
7967
7968 (define_insn "sse_ldmxcsr"
7969   [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")]
7970                     UNSPECV_LDMXCSR)]
7971   "TARGET_SSE"
7972   "%vldmxcsr\t%0"
7973   [(set_attr "type" "sse")
7974    (set_attr "atom_sse_attr" "mxcsr")
7975    (set_attr "prefix" "maybe_vex")
7976    (set_attr "memory" "load")])
7977
7978 (define_insn "sse_stmxcsr"
7979   [(set (match_operand:SI 0 "memory_operand" "=m")
7980         (unspec_volatile:SI [(const_int 0)] UNSPECV_STMXCSR))]
7981   "TARGET_SSE"
7982   "%vstmxcsr\t%0"
7983   [(set_attr "type" "sse")
7984    (set_attr "atom_sse_attr" "mxcsr")
7985    (set_attr "prefix" "maybe_vex")
7986    (set_attr "memory" "store")])
7987
7988 (define_expand "sse_sfence"
7989   [(set (match_dup 0)
7990         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
7991   "TARGET_SSE || TARGET_3DNOW_A"
7992 {
7993   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
7994   MEM_VOLATILE_P (operands[0]) = 1;
7995 })
7996
7997 (define_insn "*sse_sfence"
7998   [(set (match_operand:BLK 0 "" "")
7999         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
8000   "TARGET_SSE || TARGET_3DNOW_A"
8001   "sfence"
8002   [(set_attr "type" "sse")
8003    (set_attr "length_address" "0")
8004    (set_attr "atom_sse_attr" "fence")
8005    (set_attr "memory" "unknown")])
8006
8007 (define_insn "sse2_clflush"
8008   [(unspec_volatile [(match_operand 0 "address_operand" "p")]
8009                     UNSPECV_CLFLUSH)]
8010   "TARGET_SSE2"
8011   "clflush\t%a0"
8012   [(set_attr "type" "sse")
8013    (set_attr "atom_sse_attr" "fence")
8014    (set_attr "memory" "unknown")])
8015
8016 (define_expand "sse2_mfence"
8017   [(set (match_dup 0)
8018         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
8019   "TARGET_SSE2"
8020 {
8021   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
8022   MEM_VOLATILE_P (operands[0]) = 1;
8023 })
8024
8025 (define_insn "*sse2_mfence"
8026   [(set (match_operand:BLK 0 "" "")
8027         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
8028   "TARGET_64BIT || TARGET_SSE2"
8029   "mfence"
8030   [(set_attr "type" "sse")
8031    (set_attr "length_address" "0")
8032    (set_attr "atom_sse_attr" "fence")
8033    (set_attr "memory" "unknown")])
8034
8035 (define_expand "sse2_lfence"
8036   [(set (match_dup 0)
8037         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
8038   "TARGET_SSE2"
8039 {
8040   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
8041   MEM_VOLATILE_P (operands[0]) = 1;
8042 })
8043
8044 (define_insn "*sse2_lfence"
8045   [(set (match_operand:BLK 0 "" "")
8046         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
8047   "TARGET_SSE2"
8048   "lfence"
8049   [(set_attr "type" "sse")
8050    (set_attr "length_address" "0")
8051    (set_attr "atom_sse_attr" "lfence")
8052    (set_attr "memory" "unknown")])
8053
8054 (define_insn "sse3_mwait"
8055   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
8056                      (match_operand:SI 1 "register_operand" "c")]
8057                     UNSPECV_MWAIT)]
8058   "TARGET_SSE3"
8059 ;; 64bit version is "mwait %rax,%rcx". But only lower 32bits are used.
8060 ;; Since 32bit register operands are implicitly zero extended to 64bit,
8061 ;; we only need to set up 32bit registers.
8062   "mwait"
8063   [(set_attr "length" "3")])
8064
8065 (define_insn "sse3_monitor"
8066   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
8067                      (match_operand:SI 1 "register_operand" "c")
8068                      (match_operand:SI 2 "register_operand" "d")]
8069                     UNSPECV_MONITOR)]
8070   "TARGET_SSE3 && !TARGET_64BIT"
8071   "monitor\t%0, %1, %2"
8072   [(set_attr "length" "3")])
8073
8074 (define_insn "sse3_monitor64"
8075   [(unspec_volatile [(match_operand:DI 0 "register_operand" "a")
8076                      (match_operand:SI 1 "register_operand" "c")
8077                      (match_operand:SI 2 "register_operand" "d")]
8078                     UNSPECV_MONITOR)]
8079   "TARGET_SSE3 && TARGET_64BIT"
8080 ;; 64bit version is "monitor %rax,%rcx,%rdx". But only lower 32bits in
8081 ;; RCX and RDX are used.  Since 32bit register operands are implicitly
8082 ;; zero extended to 64bit, we only need to set up 32bit registers.
8083   "monitor"
8084   [(set_attr "length" "3")])
8085
8086 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8087 ;;
8088 ;; SSSE3 instructions
8089 ;;
8090 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8091
8092 (define_insn "avx2_phaddwv16hi3"
8093   [(set (match_operand:V16HI 0 "register_operand" "=x")
8094         (vec_concat:V16HI
8095           (vec_concat:V8HI
8096             (vec_concat:V4HI
8097               (vec_concat:V2HI
8098                 (plus:HI
8099                   (vec_select:HI
8100                     (match_operand:V16HI 1 "register_operand" "x")
8101                     (parallel [(const_int 0)]))
8102                   (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8103                 (plus:HI
8104                   (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8105                   (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8106               (vec_concat:V2HI
8107                 (plus:HI
8108                   (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8109                   (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8110                 (plus:HI
8111                   (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8112                   (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8113             (vec_concat:V4HI
8114               (vec_concat:V2HI
8115                 (plus:HI
8116                   (vec_select:HI (match_dup 1) (parallel [(const_int 8)]))
8117                   (vec_select:HI (match_dup 1) (parallel [(const_int 9)])))
8118                 (plus:HI
8119                   (vec_select:HI (match_dup 1) (parallel [(const_int 10)]))
8120                   (vec_select:HI (match_dup 1) (parallel [(const_int 11)]))))
8121               (vec_concat:V2HI
8122                 (plus:HI
8123                   (vec_select:HI (match_dup 1) (parallel [(const_int 12)]))
8124                   (vec_select:HI (match_dup 1) (parallel [(const_int 13)])))
8125                 (plus:HI
8126                   (vec_select:HI (match_dup 1) (parallel [(const_int 14)]))
8127                   (vec_select:HI (match_dup 1) (parallel [(const_int 15)]))))))
8128           (vec_concat:V8HI
8129             (vec_concat:V4HI
8130               (vec_concat:V2HI
8131                 (plus:HI
8132                   (vec_select:HI
8133                     (match_operand:V16HI 2 "nonimmediate_operand" "xm")
8134                     (parallel [(const_int 0)]))
8135                   (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8136                 (plus:HI
8137                   (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8138                   (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8139               (vec_concat:V2HI
8140                 (plus:HI
8141                   (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8142                   (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8143                 (plus:HI
8144                   (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8145                   (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))
8146             (vec_concat:V4HI
8147               (vec_concat:V2HI
8148                 (plus:HI
8149                   (vec_select:HI (match_dup 2) (parallel [(const_int 8)]))
8150                   (vec_select:HI (match_dup 2) (parallel [(const_int 9)])))
8151                 (plus:HI
8152                   (vec_select:HI (match_dup 2) (parallel [(const_int 10)]))
8153                   (vec_select:HI (match_dup 2) (parallel [(const_int 11)]))))
8154               (vec_concat:V2HI
8155                 (plus:HI
8156                   (vec_select:HI (match_dup 2) (parallel [(const_int 12)]))
8157                   (vec_select:HI (match_dup 2) (parallel [(const_int 13)])))
8158                 (plus:HI
8159                   (vec_select:HI (match_dup 2) (parallel [(const_int 14)]))
8160                   (vec_select:HI (match_dup 2) (parallel [(const_int 15)]))))))))]
8161   "TARGET_AVX2"
8162   "vphaddw\t{%2, %1, %0|%0, %1, %2}"
8163   [(set_attr "type" "sseiadd")
8164    (set_attr "prefix_extra" "1")
8165    (set_attr "prefix" "vex")
8166    (set_attr "mode" "OI")])
8167
8168 (define_insn "ssse3_phaddwv8hi3"
8169   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
8170         (vec_concat:V8HI
8171           (vec_concat:V4HI
8172             (vec_concat:V2HI
8173               (plus:HI
8174                 (vec_select:HI
8175                   (match_operand:V8HI 1 "register_operand" "0,x")
8176                   (parallel [(const_int 0)]))
8177                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8178               (plus:HI
8179                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8180                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8181             (vec_concat:V2HI
8182               (plus:HI
8183                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8184                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8185               (plus:HI
8186                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8187                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8188           (vec_concat:V4HI
8189             (vec_concat:V2HI
8190               (plus:HI
8191                 (vec_select:HI
8192                   (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
8193                   (parallel [(const_int 0)]))
8194                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8195               (plus:HI
8196                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8197                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8198             (vec_concat:V2HI
8199               (plus:HI
8200                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8201                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8202               (plus:HI
8203                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8204                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8205   "TARGET_SSSE3"
8206   "@
8207    phaddw\t{%2, %0|%0, %2}
8208    vphaddw\t{%2, %1, %0|%0, %1, %2}"
8209   [(set_attr "isa" "noavx,avx")
8210    (set_attr "type" "sseiadd")
8211    (set_attr "atom_unit" "complex")
8212    (set_attr "prefix_data16" "1,*")
8213    (set_attr "prefix_extra" "1")
8214    (set_attr "prefix" "orig,vex")
8215    (set_attr "mode" "TI")])
8216
8217 (define_insn "ssse3_phaddwv4hi3"
8218   [(set (match_operand:V4HI 0 "register_operand" "=y")
8219         (vec_concat:V4HI
8220           (vec_concat:V2HI
8221             (plus:HI
8222               (vec_select:HI
8223                 (match_operand:V4HI 1 "register_operand" "0")
8224                 (parallel [(const_int 0)]))
8225               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8226             (plus:HI
8227               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8228               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8229           (vec_concat:V2HI
8230             (plus:HI
8231               (vec_select:HI
8232                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8233                 (parallel [(const_int 0)]))
8234               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8235             (plus:HI
8236               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8237               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8238   "TARGET_SSSE3"
8239   "phaddw\t{%2, %0|%0, %2}"
8240   [(set_attr "type" "sseiadd")
8241    (set_attr "atom_unit" "complex")
8242    (set_attr "prefix_extra" "1")
8243    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8244    (set_attr "mode" "DI")])
8245
8246 (define_insn "avx2_phadddv8si3"
8247   [(set (match_operand:V8SI 0 "register_operand" "=x")
8248         (vec_concat:V8SI
8249           (vec_concat:V4SI
8250             (vec_concat:V2SI
8251               (plus:SI
8252                 (vec_select:SI
8253                   (match_operand:V8SI 1 "register_operand" "x")
8254                   (parallel [(const_int 0)]))
8255                 (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8256               (plus:SI
8257                 (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8258                 (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8259             (vec_concat:V2SI
8260               (plus:SI
8261                 (vec_select:SI (match_dup 1) (parallel [(const_int 4)]))
8262                 (vec_select:SI (match_dup 1) (parallel [(const_int 5)])))
8263               (plus:SI
8264                 (vec_select:SI (match_dup 1) (parallel [(const_int 6)]))
8265                 (vec_select:SI (match_dup 1) (parallel [(const_int 7)])))))
8266           (vec_concat:V4SI
8267             (vec_concat:V2SI
8268               (plus:SI
8269                 (vec_select:SI
8270                   (match_operand:V8SI 2 "nonimmediate_operand" "xm")
8271                   (parallel [(const_int 0)]))
8272                 (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8273               (plus:SI
8274                 (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8275                 (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))
8276             (vec_concat:V2SI
8277               (plus:SI
8278                 (vec_select:SI (match_dup 2) (parallel [(const_int 4)]))
8279                 (vec_select:SI (match_dup 2) (parallel [(const_int 5)])))
8280               (plus:SI
8281                 (vec_select:SI (match_dup 2) (parallel [(const_int 6)]))
8282                 (vec_select:SI (match_dup 2) (parallel [(const_int 7)])))))))]
8283   "TARGET_AVX2"
8284   "vphaddd\t{%2, %1, %0|%0, %1, %2}"
8285   [(set_attr "type" "sseiadd")
8286    (set_attr "prefix_extra" "1")
8287    (set_attr "prefix" "vex")
8288    (set_attr "mode" "OI")])
8289
8290 (define_insn "ssse3_phadddv4si3"
8291   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
8292         (vec_concat:V4SI
8293           (vec_concat:V2SI
8294             (plus:SI
8295               (vec_select:SI
8296                 (match_operand:V4SI 1 "register_operand" "0,x")
8297                 (parallel [(const_int 0)]))
8298               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8299             (plus:SI
8300               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8301               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8302           (vec_concat:V2SI
8303             (plus:SI
8304               (vec_select:SI
8305                 (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm")
8306                 (parallel [(const_int 0)]))
8307               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8308             (plus:SI
8309               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8310               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
8311   "TARGET_SSSE3"
8312   "@
8313    phaddd\t{%2, %0|%0, %2}
8314    vphaddd\t{%2, %1, %0|%0, %1, %2}"
8315   [(set_attr "isa" "noavx,avx")
8316    (set_attr "type" "sseiadd")
8317    (set_attr "atom_unit" "complex")
8318    (set_attr "prefix_data16" "1,*")
8319    (set_attr "prefix_extra" "1")
8320    (set_attr "prefix" "orig,vex")
8321    (set_attr "mode" "TI")])
8322
8323 (define_insn "ssse3_phadddv2si3"
8324   [(set (match_operand:V2SI 0 "register_operand" "=y")
8325         (vec_concat:V2SI
8326           (plus:SI
8327             (vec_select:SI
8328               (match_operand:V2SI 1 "register_operand" "0")
8329               (parallel [(const_int 0)]))
8330             (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8331           (plus:SI
8332             (vec_select:SI
8333               (match_operand:V2SI 2 "nonimmediate_operand" "ym")
8334               (parallel [(const_int 0)]))
8335             (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))))]
8336   "TARGET_SSSE3"
8337   "phaddd\t{%2, %0|%0, %2}"
8338   [(set_attr "type" "sseiadd")
8339    (set_attr "atom_unit" "complex")
8340    (set_attr "prefix_extra" "1")
8341    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8342    (set_attr "mode" "DI")])
8343
8344 (define_insn "avx2_phaddswv16hi3"
8345   [(set (match_operand:V16HI 0 "register_operand" "=x")
8346         (vec_concat:V16HI
8347           (vec_concat:V8HI
8348             (vec_concat:V4HI
8349               (vec_concat:V2HI
8350                 (ss_plus:HI
8351                   (vec_select:HI
8352                     (match_operand:V16HI 1 "register_operand" "x")
8353                     (parallel [(const_int 0)]))
8354                   (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8355                 (ss_plus:HI
8356                   (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8357                   (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8358               (vec_concat:V2HI
8359                 (ss_plus:HI
8360                   (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8361                   (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8362                 (ss_plus:HI
8363                   (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8364                   (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8365             (vec_concat:V4HI
8366               (vec_concat:V2HI
8367                 (ss_plus:HI
8368                   (vec_select:HI (match_dup 1) (parallel [(const_int 8)]))
8369                   (vec_select:HI (match_dup 1) (parallel [(const_int 9)])))
8370                 (ss_plus:HI
8371                   (vec_select:HI (match_dup 1) (parallel [(const_int 10)]))
8372                   (vec_select:HI (match_dup 1) (parallel [(const_int 11)]))))
8373               (vec_concat:V2HI
8374                 (ss_plus:HI
8375                   (vec_select:HI (match_dup 1) (parallel [(const_int 12)]))
8376                   (vec_select:HI (match_dup 1) (parallel [(const_int 13)])))
8377                 (ss_plus:HI
8378                   (vec_select:HI (match_dup 1) (parallel [(const_int 14)]))
8379                   (vec_select:HI (match_dup 1) (parallel [(const_int 15)]))))))
8380           (vec_concat:V8HI
8381             (vec_concat:V4HI
8382               (vec_concat:V2HI
8383                 (ss_plus:HI
8384                   (vec_select:HI
8385                     (match_operand:V16HI 2 "nonimmediate_operand" "xm")
8386                     (parallel [(const_int 0)]))
8387                   (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8388                 (ss_plus:HI
8389                   (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8390                   (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8391               (vec_concat:V2HI
8392                 (ss_plus:HI
8393                   (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8394                   (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8395                 (ss_plus:HI
8396                   (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8397                   (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))
8398             (vec_concat:V4HI
8399               (vec_concat:V2HI
8400                 (ss_plus:HI
8401                   (vec_select:HI (match_dup 2) (parallel [(const_int 8)]))
8402                   (vec_select:HI (match_dup 2) (parallel [(const_int 9)])))
8403                 (ss_plus:HI
8404                   (vec_select:HI (match_dup 2) (parallel [(const_int 10)]))
8405                   (vec_select:HI (match_dup 2) (parallel [(const_int 11)]))))
8406               (vec_concat:V2HI
8407                 (ss_plus:HI
8408                   (vec_select:HI (match_dup 2) (parallel [(const_int 12)]))
8409                   (vec_select:HI (match_dup 2) (parallel [(const_int 13)])))
8410                 (ss_plus:HI
8411                   (vec_select:HI (match_dup 2) (parallel [(const_int 14)]))
8412                   (vec_select:HI (match_dup 2) (parallel [(const_int 15)]))))))))]
8413   "TARGET_AVX2"
8414   "vphaddsw\t{%2, %1, %0|%0, %1, %2}"
8415   [(set_attr "type" "sseiadd")
8416    (set_attr "prefix_extra" "1")
8417    (set_attr "prefix" "vex")
8418    (set_attr "mode" "OI")])
8419
8420 (define_insn "ssse3_phaddswv8hi3"
8421   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
8422         (vec_concat:V8HI
8423           (vec_concat:V4HI
8424             (vec_concat:V2HI
8425               (ss_plus:HI
8426                 (vec_select:HI
8427                   (match_operand:V8HI 1 "register_operand" "0,x")
8428                   (parallel [(const_int 0)]))
8429                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8430               (ss_plus:HI
8431                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8432                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8433             (vec_concat:V2HI
8434               (ss_plus:HI
8435                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8436                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8437               (ss_plus:HI
8438                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8439                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8440           (vec_concat:V4HI
8441             (vec_concat:V2HI
8442               (ss_plus:HI
8443                 (vec_select:HI
8444                   (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
8445                   (parallel [(const_int 0)]))
8446                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8447               (ss_plus:HI
8448                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8449                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8450             (vec_concat:V2HI
8451               (ss_plus:HI
8452                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8453                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8454               (ss_plus:HI
8455                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8456                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8457   "TARGET_SSSE3"
8458   "@
8459    phaddsw\t{%2, %0|%0, %2}
8460    vphaddsw\t{%2, %1, %0|%0, %1, %2}"
8461   [(set_attr "isa" "noavx,avx")
8462    (set_attr "type" "sseiadd")
8463    (set_attr "atom_unit" "complex")
8464    (set_attr "prefix_data16" "1,*")
8465    (set_attr "prefix_extra" "1")
8466    (set_attr "prefix" "orig,vex")
8467    (set_attr "mode" "TI")])
8468
8469 (define_insn "ssse3_phaddswv4hi3"
8470   [(set (match_operand:V4HI 0 "register_operand" "=y")
8471         (vec_concat:V4HI
8472           (vec_concat:V2HI
8473             (ss_plus:HI
8474               (vec_select:HI
8475                 (match_operand:V4HI 1 "register_operand" "0")
8476                 (parallel [(const_int 0)]))
8477               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8478             (ss_plus:HI
8479               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8480               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8481           (vec_concat:V2HI
8482             (ss_plus:HI
8483               (vec_select:HI
8484                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8485                 (parallel [(const_int 0)]))
8486               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8487             (ss_plus:HI
8488               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8489               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8490   "TARGET_SSSE3"
8491   "phaddsw\t{%2, %0|%0, %2}"
8492   [(set_attr "type" "sseiadd")
8493    (set_attr "atom_unit" "complex")
8494    (set_attr "prefix_extra" "1")
8495    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8496    (set_attr "mode" "DI")])
8497
8498 (define_insn "avx2_phsubwv16hi3"
8499   [(set (match_operand:V16HI 0 "register_operand" "=x")
8500         (vec_concat:V16HI
8501           (vec_concat:V8HI
8502             (vec_concat:V4HI
8503               (vec_concat:V2HI
8504                 (minus:HI
8505                   (vec_select:HI
8506                     (match_operand:V16HI 1 "register_operand" "x")
8507                     (parallel [(const_int 0)]))
8508                   (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8509                 (minus:HI
8510                   (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8511                   (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8512               (vec_concat:V2HI
8513                 (minus:HI
8514                   (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8515                   (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8516                 (minus:HI
8517                   (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8518                   (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8519             (vec_concat:V4HI
8520               (vec_concat:V2HI
8521                 (minus:HI
8522                   (vec_select:HI (match_dup 1) (parallel [(const_int 8)]))
8523                   (vec_select:HI (match_dup 1) (parallel [(const_int 9)])))
8524                 (minus:HI
8525                   (vec_select:HI (match_dup 1) (parallel [(const_int 10)]))
8526                   (vec_select:HI (match_dup 1) (parallel [(const_int 11)]))))
8527               (vec_concat:V2HI
8528                 (minus:HI
8529                   (vec_select:HI (match_dup 1) (parallel [(const_int 12)]))
8530                   (vec_select:HI (match_dup 1) (parallel [(const_int 13)])))
8531                 (minus:HI
8532                   (vec_select:HI (match_dup 1) (parallel [(const_int 14)]))
8533                   (vec_select:HI (match_dup 1) (parallel [(const_int 15)]))))))
8534           (vec_concat:V8HI
8535             (vec_concat:V4HI
8536               (vec_concat:V2HI
8537                 (minus:HI
8538                   (vec_select:HI
8539                     (match_operand:V16HI 2 "nonimmediate_operand" "xm")
8540                     (parallel [(const_int 0)]))
8541                   (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8542                 (minus:HI
8543                   (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8544                   (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8545               (vec_concat:V2HI
8546                 (minus:HI
8547                   (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8548                   (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8549                 (minus:HI
8550                   (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8551                   (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))
8552             (vec_concat:V4HI
8553               (vec_concat:V2HI
8554                 (minus:HI
8555                   (vec_select:HI (match_dup 2) (parallel [(const_int 8)]))
8556                   (vec_select:HI (match_dup 2) (parallel [(const_int 9)])))
8557                 (minus:HI
8558                   (vec_select:HI (match_dup 2) (parallel [(const_int 10)]))
8559                   (vec_select:HI (match_dup 2) (parallel [(const_int 11)]))))
8560               (vec_concat:V2HI
8561                 (minus:HI
8562                   (vec_select:HI (match_dup 2) (parallel [(const_int 12)]))
8563                   (vec_select:HI (match_dup 2) (parallel [(const_int 13)])))
8564                 (minus:HI
8565                   (vec_select:HI (match_dup 2) (parallel [(const_int 14)]))
8566                   (vec_select:HI (match_dup 2) (parallel [(const_int 15)]))))))))]
8567   "TARGET_AVX2"
8568   "vphsubw\t{%2, %1, %0|%0, %1, %2}"
8569   [(set_attr "type" "sseiadd")
8570    (set_attr "prefix_extra" "1")
8571    (set_attr "prefix" "vex")
8572    (set_attr "mode" "OI")])
8573
8574 (define_insn "ssse3_phsubwv8hi3"
8575   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
8576         (vec_concat:V8HI
8577           (vec_concat:V4HI
8578             (vec_concat:V2HI
8579               (minus:HI
8580                 (vec_select:HI
8581                   (match_operand:V8HI 1 "register_operand" "0,x")
8582                   (parallel [(const_int 0)]))
8583                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8584               (minus:HI
8585                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8586                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8587             (vec_concat:V2HI
8588               (minus:HI
8589                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8590                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8591               (minus:HI
8592                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8593                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8594           (vec_concat:V4HI
8595             (vec_concat:V2HI
8596               (minus:HI
8597                 (vec_select:HI
8598                   (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
8599                   (parallel [(const_int 0)]))
8600                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8601               (minus:HI
8602                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8603                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8604             (vec_concat:V2HI
8605               (minus:HI
8606                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8607                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8608               (minus:HI
8609                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8610                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8611   "TARGET_SSSE3"
8612   "@
8613    phsubw\t{%2, %0|%0, %2}
8614    vphsubw\t{%2, %1, %0|%0, %1, %2}"
8615   [(set_attr "isa" "noavx,avx")
8616    (set_attr "type" "sseiadd")
8617    (set_attr "atom_unit" "complex")
8618    (set_attr "prefix_data16" "1,*")
8619    (set_attr "prefix_extra" "1")
8620    (set_attr "prefix" "orig,vex")
8621    (set_attr "mode" "TI")])
8622
8623 (define_insn "ssse3_phsubwv4hi3"
8624   [(set (match_operand:V4HI 0 "register_operand" "=y")
8625         (vec_concat:V4HI
8626           (vec_concat:V2HI
8627             (minus:HI
8628               (vec_select:HI
8629                 (match_operand:V4HI 1 "register_operand" "0")
8630                 (parallel [(const_int 0)]))
8631               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8632             (minus:HI
8633               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8634               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8635           (vec_concat:V2HI
8636             (minus:HI
8637               (vec_select:HI
8638                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8639                 (parallel [(const_int 0)]))
8640               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8641             (minus:HI
8642               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8643               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8644   "TARGET_SSSE3"
8645   "phsubw\t{%2, %0|%0, %2}"
8646   [(set_attr "type" "sseiadd")
8647    (set_attr "atom_unit" "complex")
8648    (set_attr "prefix_extra" "1")
8649    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8650    (set_attr "mode" "DI")])
8651
8652 (define_insn "avx2_phsubdv8si3"
8653   [(set (match_operand:V8SI 0 "register_operand" "=x")
8654         (vec_concat:V8SI
8655           (vec_concat:V4SI
8656             (vec_concat:V2SI
8657               (minus:SI
8658                 (vec_select:SI
8659                   (match_operand:V8SI 1 "register_operand" "x")
8660                   (parallel [(const_int 0)]))
8661                 (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8662               (minus:SI
8663                 (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8664                 (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8665             (vec_concat:V2SI
8666               (minus:SI
8667                 (vec_select:SI (match_dup 1) (parallel [(const_int 4)]))
8668                 (vec_select:SI (match_dup 1) (parallel [(const_int 5)])))
8669               (minus:SI
8670                 (vec_select:SI (match_dup 1) (parallel [(const_int 6)]))
8671                 (vec_select:SI (match_dup 1) (parallel [(const_int 7)])))))
8672           (vec_concat:V4SI
8673             (vec_concat:V2SI
8674               (minus:SI
8675                 (vec_select:SI
8676                   (match_operand:V8SI 2 "nonimmediate_operand" "xm")
8677                   (parallel [(const_int 0)]))
8678                 (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8679               (minus:SI
8680                 (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8681                 (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))
8682             (vec_concat:V2SI
8683               (minus:SI
8684                 (vec_select:SI (match_dup 2) (parallel [(const_int 4)]))
8685                 (vec_select:SI (match_dup 2) (parallel [(const_int 5)])))
8686               (minus:SI
8687                 (vec_select:SI (match_dup 2) (parallel [(const_int 6)]))
8688                 (vec_select:SI (match_dup 2) (parallel [(const_int 7)])))))))]
8689   "TARGET_AVX2"
8690   "vphsubd\t{%2, %1, %0|%0, %1, %2}"
8691   [(set_attr "type" "sseiadd")
8692    (set_attr "prefix_extra" "1")
8693    (set_attr "prefix" "vex")
8694    (set_attr "mode" "OI")])
8695
8696 (define_insn "ssse3_phsubdv4si3"
8697   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
8698         (vec_concat:V4SI
8699           (vec_concat:V2SI
8700             (minus:SI
8701               (vec_select:SI
8702                 (match_operand:V4SI 1 "register_operand" "0,x")
8703                 (parallel [(const_int 0)]))
8704               (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8705             (minus:SI
8706               (vec_select:SI (match_dup 1) (parallel [(const_int 2)]))
8707               (vec_select:SI (match_dup 1) (parallel [(const_int 3)]))))
8708           (vec_concat:V2SI
8709             (minus:SI
8710               (vec_select:SI
8711                 (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm")
8712                 (parallel [(const_int 0)]))
8713               (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))
8714             (minus:SI
8715               (vec_select:SI (match_dup 2) (parallel [(const_int 2)]))
8716               (vec_select:SI (match_dup 2) (parallel [(const_int 3)]))))))]
8717   "TARGET_SSSE3"
8718   "@
8719    phsubd\t{%2, %0|%0, %2}
8720    vphsubd\t{%2, %1, %0|%0, %1, %2}"
8721
8722   [(set_attr "isa" "noavx,avx")
8723    (set_attr "type" "sseiadd")
8724    (set_attr "atom_unit" "complex")
8725    (set_attr "prefix_data16" "1,*")
8726    (set_attr "prefix_extra" "1")
8727    (set_attr "prefix" "orig,vex")
8728    (set_attr "mode" "TI")])
8729
8730 (define_insn "ssse3_phsubdv2si3"
8731   [(set (match_operand:V2SI 0 "register_operand" "=y")
8732         (vec_concat:V2SI
8733           (minus:SI
8734             (vec_select:SI
8735               (match_operand:V2SI 1 "register_operand" "0")
8736               (parallel [(const_int 0)]))
8737             (vec_select:SI (match_dup 1) (parallel [(const_int 1)])))
8738           (minus:SI
8739             (vec_select:SI
8740               (match_operand:V2SI 2 "nonimmediate_operand" "ym")
8741               (parallel [(const_int 0)]))
8742             (vec_select:SI (match_dup 2) (parallel [(const_int 1)])))))]
8743   "TARGET_SSSE3"
8744   "phsubd\t{%2, %0|%0, %2}"
8745   [(set_attr "type" "sseiadd")
8746    (set_attr "atom_unit" "complex")
8747    (set_attr "prefix_extra" "1")
8748    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8749    (set_attr "mode" "DI")])
8750
8751 (define_insn "avx2_phsubswv16hi3"
8752   [(set (match_operand:V16HI 0 "register_operand" "=x")
8753         (vec_concat:V16HI
8754           (vec_concat:V8HI
8755             (vec_concat:V4HI
8756               (vec_concat:V2HI
8757                 (ss_minus:HI
8758                   (vec_select:HI
8759                     (match_operand:V16HI 1 "register_operand" "x")
8760                     (parallel [(const_int 0)]))
8761                   (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8762                 (ss_minus:HI
8763                   (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8764                   (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8765               (vec_concat:V2HI
8766                 (ss_minus:HI
8767                   (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8768                   (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8769                 (ss_minus:HI
8770                   (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8771                   (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8772             (vec_concat:V4HI
8773               (vec_concat:V2HI
8774                 (ss_minus:HI
8775                   (vec_select:HI (match_dup 1) (parallel [(const_int 8)]))
8776                   (vec_select:HI (match_dup 1) (parallel [(const_int 9)])))
8777                 (ss_minus:HI
8778                   (vec_select:HI (match_dup 1) (parallel [(const_int 10)]))
8779                   (vec_select:HI (match_dup 1) (parallel [(const_int 11)]))))
8780               (vec_concat:V2HI
8781                 (ss_minus:HI
8782                   (vec_select:HI (match_dup 1) (parallel [(const_int 12)]))
8783                   (vec_select:HI (match_dup 1) (parallel [(const_int 13)])))
8784                 (ss_minus:HI
8785                   (vec_select:HI (match_dup 1) (parallel [(const_int 14)]))
8786                   (vec_select:HI (match_dup 1) (parallel [(const_int 15)]))))))
8787           (vec_concat:V8HI
8788             (vec_concat:V4HI
8789               (vec_concat:V2HI
8790                 (ss_minus:HI
8791                   (vec_select:HI
8792                     (match_operand:V16HI 2 "nonimmediate_operand" "xm")
8793                     (parallel [(const_int 0)]))
8794                   (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8795                 (ss_minus:HI
8796                   (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8797                   (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8798               (vec_concat:V2HI
8799                 (ss_minus:HI
8800                   (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8801                   (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8802                 (ss_minus:HI
8803                   (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8804                   (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))
8805             (vec_concat:V4HI
8806               (vec_concat:V2HI
8807                 (ss_minus:HI
8808                   (vec_select:HI (match_dup 2) (parallel [(const_int 8)]))
8809                   (vec_select:HI (match_dup 2) (parallel [(const_int 9)])))
8810                 (ss_minus:HI
8811                   (vec_select:HI (match_dup 2) (parallel [(const_int 10)]))
8812                   (vec_select:HI (match_dup 2) (parallel [(const_int 11)]))))
8813               (vec_concat:V2HI
8814                 (ss_minus:HI
8815                   (vec_select:HI (match_dup 2) (parallel [(const_int 12)]))
8816                   (vec_select:HI (match_dup 2) (parallel [(const_int 13)])))
8817                 (ss_minus:HI
8818                   (vec_select:HI (match_dup 2) (parallel [(const_int 14)]))
8819                   (vec_select:HI (match_dup 2) (parallel [(const_int 15)]))))))))]
8820   "TARGET_AVX2"
8821   "vphsubsw\t{%2, %1, %0|%0, %1, %2}"
8822   [(set_attr "type" "sseiadd")
8823    (set_attr "prefix_extra" "1")
8824    (set_attr "prefix" "vex")
8825    (set_attr "mode" "OI")])
8826
8827 (define_insn "ssse3_phsubswv8hi3"
8828   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
8829         (vec_concat:V8HI
8830           (vec_concat:V4HI
8831             (vec_concat:V2HI
8832               (ss_minus:HI
8833                 (vec_select:HI
8834                   (match_operand:V8HI 1 "register_operand" "0,x")
8835                   (parallel [(const_int 0)]))
8836                 (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8837               (ss_minus:HI
8838                 (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8839                 (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8840             (vec_concat:V2HI
8841               (ss_minus:HI
8842                 (vec_select:HI (match_dup 1) (parallel [(const_int 4)]))
8843                 (vec_select:HI (match_dup 1) (parallel [(const_int 5)])))
8844               (ss_minus:HI
8845                 (vec_select:HI (match_dup 1) (parallel [(const_int 6)]))
8846                 (vec_select:HI (match_dup 1) (parallel [(const_int 7)])))))
8847           (vec_concat:V4HI
8848             (vec_concat:V2HI
8849               (ss_minus:HI
8850                 (vec_select:HI
8851                   (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
8852                   (parallel [(const_int 0)]))
8853                 (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8854               (ss_minus:HI
8855                 (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8856                 (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))
8857             (vec_concat:V2HI
8858               (ss_minus:HI
8859                 (vec_select:HI (match_dup 2) (parallel [(const_int 4)]))
8860                 (vec_select:HI (match_dup 2) (parallel [(const_int 5)])))
8861               (ss_minus:HI
8862                 (vec_select:HI (match_dup 2) (parallel [(const_int 6)]))
8863                 (vec_select:HI (match_dup 2) (parallel [(const_int 7)])))))))]
8864   "TARGET_SSSE3"
8865   "@
8866    phsubsw\t{%2, %0|%0, %2}
8867    vphsubsw\t{%2, %1, %0|%0, %1, %2}"
8868   [(set_attr "isa" "noavx,avx")
8869    (set_attr "type" "sseiadd")
8870    (set_attr "atom_unit" "complex")
8871    (set_attr "prefix_data16" "1,*")
8872    (set_attr "prefix_extra" "1")
8873    (set_attr "prefix" "orig,vex")
8874    (set_attr "mode" "TI")])
8875
8876 (define_insn "ssse3_phsubswv4hi3"
8877   [(set (match_operand:V4HI 0 "register_operand" "=y")
8878         (vec_concat:V4HI
8879           (vec_concat:V2HI
8880             (ss_minus:HI
8881               (vec_select:HI
8882                 (match_operand:V4HI 1 "register_operand" "0")
8883                 (parallel [(const_int 0)]))
8884               (vec_select:HI (match_dup 1) (parallel [(const_int 1)])))
8885             (ss_minus:HI
8886               (vec_select:HI (match_dup 1) (parallel [(const_int 2)]))
8887               (vec_select:HI (match_dup 1) (parallel [(const_int 3)]))))
8888           (vec_concat:V2HI
8889             (ss_minus:HI
8890               (vec_select:HI
8891                 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
8892                 (parallel [(const_int 0)]))
8893               (vec_select:HI (match_dup 2) (parallel [(const_int 1)])))
8894             (ss_minus:HI
8895               (vec_select:HI (match_dup 2) (parallel [(const_int 2)]))
8896               (vec_select:HI (match_dup 2) (parallel [(const_int 3)]))))))]
8897   "TARGET_SSSE3"
8898   "phsubsw\t{%2, %0|%0, %2}"
8899   [(set_attr "type" "sseiadd")
8900    (set_attr "atom_unit" "complex")
8901    (set_attr "prefix_extra" "1")
8902    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
8903    (set_attr "mode" "DI")])
8904
8905 (define_insn "avx2_pmaddubsw256"
8906   [(set (match_operand:V16HI 0 "register_operand" "=x")
8907         (ss_plus:V16HI
8908           (mult:V16HI
8909             (zero_extend:V16HI
8910               (vec_select:V16QI
8911                 (match_operand:V32QI 1 "register_operand" "x")
8912                 (parallel [(const_int 0)
8913                            (const_int 2)
8914                            (const_int 4)
8915                            (const_int 6)
8916                            (const_int 8)
8917                            (const_int 10)
8918                            (const_int 12)
8919                            (const_int 14)
8920                            (const_int 16)
8921                            (const_int 18)
8922                            (const_int 20)
8923                            (const_int 22)
8924                            (const_int 24)
8925                            (const_int 26)
8926                            (const_int 28)
8927                            (const_int 30)])))
8928             (sign_extend:V16HI
8929               (vec_select:V16QI
8930                 (match_operand:V32QI 2 "nonimmediate_operand" "xm")
8931                 (parallel [(const_int 0)
8932                            (const_int 2)
8933                            (const_int 4)
8934                            (const_int 6)
8935                            (const_int 8)
8936                            (const_int 10)
8937                            (const_int 12)
8938                            (const_int 14)
8939                            (const_int 16)
8940                            (const_int 18)
8941                            (const_int 20)
8942                            (const_int 22)
8943                            (const_int 24)
8944                            (const_int 26)
8945                            (const_int 28)
8946                            (const_int 30)]))))
8947           (mult:V16HI
8948             (zero_extend:V16HI
8949               (vec_select:V16QI (match_dup 1)
8950                 (parallel [(const_int 1)
8951                            (const_int 3)
8952                            (const_int 5)
8953                            (const_int 7)
8954                            (const_int 9)
8955                            (const_int 11)
8956                            (const_int 13)
8957                            (const_int 15)
8958                            (const_int 17)
8959                            (const_int 19)
8960                            (const_int 21)
8961                            (const_int 23)
8962                            (const_int 25)
8963                            (const_int 27)
8964                            (const_int 29)
8965                            (const_int 31)])))
8966             (sign_extend:V16HI
8967               (vec_select:V16QI (match_dup 2)
8968                 (parallel [(const_int 1)
8969                            (const_int 3)
8970                            (const_int 5)
8971                            (const_int 7)
8972                            (const_int 9)
8973                            (const_int 11)
8974                            (const_int 13)
8975                            (const_int 15)
8976                            (const_int 17)
8977                            (const_int 19)
8978                            (const_int 21)
8979                            (const_int 23)
8980                            (const_int 25)
8981                            (const_int 27)
8982                            (const_int 29)
8983                            (const_int 31)]))))))]
8984   "TARGET_AVX2"
8985   "vpmaddubsw\t{%2, %1, %0|%0, %1, %2}"
8986   [(set_attr "type" "sseiadd")
8987    (set_attr "prefix_extra" "1")
8988    (set_attr "prefix" "vex")
8989    (set_attr "mode" "OI")])
8990
8991 (define_insn "ssse3_pmaddubsw128"
8992   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
8993         (ss_plus:V8HI
8994           (mult:V8HI
8995             (zero_extend:V8HI
8996               (vec_select:V8QI
8997                 (match_operand:V16QI 1 "register_operand" "0,x")
8998                 (parallel [(const_int 0)
8999                            (const_int 2)
9000                            (const_int 4)
9001                            (const_int 6)
9002                            (const_int 8)
9003                            (const_int 10)
9004                            (const_int 12)
9005                            (const_int 14)])))
9006             (sign_extend:V8HI
9007               (vec_select:V8QI
9008                 (match_operand:V16QI 2 "nonimmediate_operand" "xm,xm")
9009                 (parallel [(const_int 0)
9010                            (const_int 2)
9011                            (const_int 4)
9012                            (const_int 6)
9013                            (const_int 8)
9014                            (const_int 10)
9015                            (const_int 12)
9016                            (const_int 14)]))))
9017           (mult:V8HI
9018             (zero_extend:V8HI
9019               (vec_select:V8QI (match_dup 1)
9020                 (parallel [(const_int 1)
9021                            (const_int 3)
9022                            (const_int 5)
9023                            (const_int 7)
9024                            (const_int 9)
9025                            (const_int 11)
9026                            (const_int 13)
9027                            (const_int 15)])))
9028             (sign_extend:V8HI
9029               (vec_select:V8QI (match_dup 2)
9030                 (parallel [(const_int 1)
9031                            (const_int 3)
9032                            (const_int 5)
9033                            (const_int 7)
9034                            (const_int 9)
9035                            (const_int 11)
9036                            (const_int 13)
9037                            (const_int 15)]))))))]
9038   "TARGET_SSSE3"
9039   "@
9040    pmaddubsw\t{%2, %0|%0, %2}
9041    vpmaddubsw\t{%2, %1, %0|%0, %1, %2}"
9042   [(set_attr "isa" "noavx,avx")
9043    (set_attr "type" "sseiadd")
9044    (set_attr "atom_unit" "simul")
9045    (set_attr "prefix_data16" "1,*")
9046    (set_attr "prefix_extra" "1")
9047    (set_attr "prefix" "orig,vex")
9048    (set_attr "mode" "TI")])
9049
9050 (define_insn "ssse3_pmaddubsw"
9051   [(set (match_operand:V4HI 0 "register_operand" "=y")
9052         (ss_plus:V4HI
9053           (mult:V4HI
9054             (zero_extend:V4HI
9055               (vec_select:V4QI
9056                 (match_operand:V8QI 1 "register_operand" "0")
9057                 (parallel [(const_int 0)
9058                            (const_int 2)
9059                            (const_int 4)
9060                            (const_int 6)])))
9061             (sign_extend:V4HI
9062               (vec_select:V4QI
9063                 (match_operand:V8QI 2 "nonimmediate_operand" "ym")
9064                 (parallel [(const_int 0)
9065                            (const_int 2)
9066                            (const_int 4)
9067                            (const_int 6)]))))
9068           (mult:V4HI
9069             (zero_extend:V4HI
9070               (vec_select:V4QI (match_dup 1)
9071                 (parallel [(const_int 1)
9072                            (const_int 3)
9073                            (const_int 5)
9074                            (const_int 7)])))
9075             (sign_extend:V4HI
9076               (vec_select:V4QI (match_dup 2)
9077                 (parallel [(const_int 1)
9078                            (const_int 3)
9079                            (const_int 5)
9080                            (const_int 7)]))))))]
9081   "TARGET_SSSE3"
9082   "pmaddubsw\t{%2, %0|%0, %2}"
9083   [(set_attr "type" "sseiadd")
9084    (set_attr "atom_unit" "simul")
9085    (set_attr "prefix_extra" "1")
9086    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9087    (set_attr "mode" "DI")])
9088
9089 (define_expand "avx2_umulhrswv16hi3"
9090   [(set (match_operand:V16HI 0 "register_operand" "")
9091         (truncate:V16HI
9092           (lshiftrt:V16SI
9093             (plus:V16SI
9094               (lshiftrt:V16SI
9095                 (mult:V16SI
9096                   (sign_extend:V16SI
9097                     (match_operand:V16HI 1 "nonimmediate_operand" ""))
9098                   (sign_extend:V16SI
9099                     (match_operand:V16HI 2 "nonimmediate_operand" "")))
9100                 (const_int 14))
9101               (const_vector:V16HI [(const_int 1) (const_int 1)
9102                                    (const_int 1) (const_int 1)
9103                                    (const_int 1) (const_int 1)
9104                                    (const_int 1) (const_int 1)
9105                                    (const_int 1) (const_int 1)
9106                                    (const_int 1) (const_int 1)
9107                                    (const_int 1) (const_int 1)
9108                                    (const_int 1) (const_int 1)]))
9109             (const_int 1))))]
9110   "TARGET_AVX2"
9111   "ix86_fixup_binary_operands_no_copy (MULT, V16HImode, operands);")
9112
9113 (define_insn "*avx2_umulhrswv16hi3"
9114   [(set (match_operand:V16HI 0 "register_operand" "=x")
9115         (truncate:V16HI
9116           (lshiftrt:V16SI
9117             (plus:V16SI
9118               (lshiftrt:V16SI
9119                 (mult:V16SI
9120                   (sign_extend:V16SI
9121                     (match_operand:V16HI 1 "nonimmediate_operand" "%x"))
9122                   (sign_extend:V16SI
9123                     (match_operand:V16HI 2 "nonimmediate_operand" "xm")))
9124                 (const_int 14))
9125               (const_vector:V16HI [(const_int 1) (const_int 1)
9126                                    (const_int 1) (const_int 1)
9127                                    (const_int 1) (const_int 1)
9128                                    (const_int 1) (const_int 1)
9129                                    (const_int 1) (const_int 1)
9130                                    (const_int 1) (const_int 1)
9131                                    (const_int 1) (const_int 1)
9132                                    (const_int 1) (const_int 1)]))
9133             (const_int 1))))]
9134   "TARGET_AVX2 && ix86_binary_operator_ok (MULT, V16HImode, operands)"
9135   "vpmulhrsw\t{%2, %1, %0|%0, %1, %2}"
9136   [(set_attr "type" "sseimul")
9137    (set_attr "prefix_extra" "1")
9138    (set_attr "prefix" "vex")
9139    (set_attr "mode" "OI")])
9140
9141 (define_expand "ssse3_pmulhrswv8hi3"
9142   [(set (match_operand:V8HI 0 "register_operand" "")
9143         (truncate:V8HI
9144           (lshiftrt:V8SI
9145             (plus:V8SI
9146               (lshiftrt:V8SI
9147                 (mult:V8SI
9148                   (sign_extend:V8SI
9149                     (match_operand:V8HI 1 "nonimmediate_operand" ""))
9150                   (sign_extend:V8SI
9151                     (match_operand:V8HI 2 "nonimmediate_operand" "")))
9152                 (const_int 14))
9153               (const_vector:V8HI [(const_int 1) (const_int 1)
9154                                   (const_int 1) (const_int 1)
9155                                   (const_int 1) (const_int 1)
9156                                   (const_int 1) (const_int 1)]))
9157             (const_int 1))))]
9158   "TARGET_SSSE3"
9159   "ix86_fixup_binary_operands_no_copy (MULT, V8HImode, operands);")
9160
9161 (define_insn "*ssse3_pmulhrswv8hi3"
9162   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
9163         (truncate:V8HI
9164           (lshiftrt:V8SI
9165             (plus:V8SI
9166               (lshiftrt:V8SI
9167                 (mult:V8SI
9168                   (sign_extend:V8SI
9169                     (match_operand:V8HI 1 "nonimmediate_operand" "%0,x"))
9170                   (sign_extend:V8SI
9171                     (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")))
9172                 (const_int 14))
9173               (const_vector:V8HI [(const_int 1) (const_int 1)
9174                                   (const_int 1) (const_int 1)
9175                                   (const_int 1) (const_int 1)
9176                                   (const_int 1) (const_int 1)]))
9177             (const_int 1))))]
9178   "TARGET_SSSE3 && ix86_binary_operator_ok (MULT, V8HImode, operands)"
9179   "@
9180    pmulhrsw\t{%2, %0|%0, %2}
9181    vpmulhrsw\t{%2, %1, %0|%0, %1, %2}"
9182   [(set_attr "isa" "noavx,avx")
9183    (set_attr "type" "sseimul")
9184    (set_attr "prefix_data16" "1,*")
9185    (set_attr "prefix_extra" "1")
9186    (set_attr "prefix" "orig,vex")
9187    (set_attr "mode" "TI")])
9188
9189 (define_expand "ssse3_pmulhrswv4hi3"
9190   [(set (match_operand:V4HI 0 "register_operand" "")
9191         (truncate:V4HI
9192           (lshiftrt:V4SI
9193             (plus:V4SI
9194               (lshiftrt:V4SI
9195                 (mult:V4SI
9196                   (sign_extend:V4SI
9197                     (match_operand:V4HI 1 "nonimmediate_operand" ""))
9198                   (sign_extend:V4SI
9199                     (match_operand:V4HI 2 "nonimmediate_operand" "")))
9200                 (const_int 14))
9201               (const_vector:V4HI [(const_int 1) (const_int 1)
9202                                   (const_int 1) (const_int 1)]))
9203             (const_int 1))))]
9204   "TARGET_SSSE3"
9205   "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
9206
9207 (define_insn "*ssse3_pmulhrswv4hi3"
9208   [(set (match_operand:V4HI 0 "register_operand" "=y")
9209         (truncate:V4HI
9210           (lshiftrt:V4SI
9211             (plus:V4SI
9212               (lshiftrt:V4SI
9213                 (mult:V4SI
9214                   (sign_extend:V4SI
9215                     (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
9216                   (sign_extend:V4SI
9217                     (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
9218                 (const_int 14))
9219               (const_vector:V4HI [(const_int 1) (const_int 1)
9220                                   (const_int 1) (const_int 1)]))
9221             (const_int 1))))]
9222   "TARGET_SSSE3 && ix86_binary_operator_ok (MULT, V4HImode, operands)"
9223   "pmulhrsw\t{%2, %0|%0, %2}"
9224   [(set_attr "type" "sseimul")
9225    (set_attr "prefix_extra" "1")
9226    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9227    (set_attr "mode" "DI")])
9228
9229 (define_insn "<ssse3_avx2>_pshufb<mode>3"
9230   [(set (match_operand:VI1_AVX2 0 "register_operand" "=x,x")
9231         (unspec:VI1_AVX2 [(match_operand:VI1_AVX2 1 "register_operand" "0,x")
9232                           (match_operand:VI1_AVX2 2 "nonimmediate_operand" "xm,xm")]
9233                          UNSPEC_PSHUFB))]
9234   "TARGET_SSSE3"
9235   "@
9236    pshufb\t{%2, %0|%0, %2}
9237    vpshufb\t{%2, %1, %0|%0, %1, %2}"
9238   [(set_attr "isa" "noavx,avx")
9239    (set_attr "type" "sselog1")
9240    (set_attr "prefix_data16" "1,*")
9241    (set_attr "prefix_extra" "1")
9242    (set_attr "prefix" "orig,vex")
9243    (set_attr "mode" "<sseinsnmode>")])
9244
9245 (define_insn "ssse3_pshufbv8qi3"
9246   [(set (match_operand:V8QI 0 "register_operand" "=y")
9247         (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "0")
9248                       (match_operand:V8QI 2 "nonimmediate_operand" "ym")]
9249                      UNSPEC_PSHUFB))]
9250   "TARGET_SSSE3"
9251   "pshufb\t{%2, %0|%0, %2}";
9252   [(set_attr "type" "sselog1")
9253    (set_attr "prefix_extra" "1")
9254    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9255    (set_attr "mode" "DI")])
9256
9257 (define_insn "<ssse3_avx2>_psign<mode>3"
9258   [(set (match_operand:VI124_AVX2 0 "register_operand" "=x,x")
9259         (unspec:VI124_AVX2
9260           [(match_operand:VI124_AVX2 1 "register_operand" "0,x")
9261            (match_operand:VI124_AVX2 2 "nonimmediate_operand" "xm,xm")]
9262           UNSPEC_PSIGN))]
9263   "TARGET_SSSE3"
9264   "@
9265    psign<ssemodesuffix>\t{%2, %0|%0, %2}
9266    vpsign<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
9267   [(set_attr "isa" "noavx,avx")
9268    (set_attr "type" "sselog1")
9269    (set_attr "prefix_data16" "1,*")
9270    (set_attr "prefix_extra" "1")
9271    (set_attr "prefix" "orig,vex")
9272    (set_attr "mode" "<sseinsnmode>")])
9273
9274 (define_insn "ssse3_psign<mode>3"
9275   [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
9276         (unspec:MMXMODEI
9277           [(match_operand:MMXMODEI 1 "register_operand" "0")
9278            (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")]
9279           UNSPEC_PSIGN))]
9280   "TARGET_SSSE3"
9281   "psign<mmxvecsize>\t{%2, %0|%0, %2}";
9282   [(set_attr "type" "sselog1")
9283    (set_attr "prefix_extra" "1")
9284    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9285    (set_attr "mode" "DI")])
9286
9287 (define_insn "<ssse3_avx2>_palignr<mode>"
9288   [(set (match_operand:SSESCALARMODE 0 "register_operand" "=x,x")
9289         (unspec:SSESCALARMODE [(match_operand:SSESCALARMODE 1 "register_operand" "0,x")
9290                                (match_operand:SSESCALARMODE 2 "nonimmediate_operand" "xm,xm")
9291                                (match_operand:SI 3 "const_0_to_255_mul_8_operand" "n,n")]
9292                               UNSPEC_PALIGNR))]
9293   "TARGET_SSSE3"
9294 {
9295   operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
9296
9297   switch (which_alternative)
9298     {
9299     case 0:
9300       return "palignr\t{%3, %2, %0|%0, %2, %3}";
9301     case 1:
9302       return "vpalignr\t{%3, %2, %1, %0|%0, %1, %2, %3}";
9303     default:
9304       gcc_unreachable ();
9305     }
9306 }
9307   [(set_attr "isa" "noavx,avx")
9308    (set_attr "type" "sseishft")
9309    (set_attr "atom_unit" "sishuf")
9310    (set_attr "prefix_data16" "1,*")
9311    (set_attr "prefix_extra" "1")
9312    (set_attr "length_immediate" "1")
9313    (set_attr "prefix" "orig,vex")
9314    (set_attr "mode" "<sseinsnmode>")])
9315
9316 (define_insn "ssse3_palignrdi"
9317   [(set (match_operand:DI 0 "register_operand" "=y")
9318         (unspec:DI [(match_operand:DI 1 "register_operand" "0")
9319                     (match_operand:DI 2 "nonimmediate_operand" "ym")
9320                     (match_operand:SI 3 "const_0_to_255_mul_8_operand" "n")]
9321                    UNSPEC_PALIGNR))]
9322   "TARGET_SSSE3"
9323 {
9324   operands[3] = GEN_INT (INTVAL (operands[3]) / 8);
9325   return "palignr\t{%3, %2, %0|%0, %2, %3}";
9326 }
9327   [(set_attr "type" "sseishft")
9328    (set_attr "atom_unit" "sishuf")
9329    (set_attr "prefix_extra" "1")
9330    (set_attr "length_immediate" "1")
9331    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9332    (set_attr "mode" "DI")])
9333
9334 (define_insn "abs<mode>2"
9335   [(set (match_operand:VI124_AVX2 0 "register_operand" "=x")
9336         (abs:VI124_AVX2
9337           (match_operand:VI124_AVX2 1 "nonimmediate_operand" "xm")))]
9338   "TARGET_SSSE3"
9339   "%vpabs<ssemodesuffix>\t{%1, %0|%0, %1}"
9340   [(set_attr "type" "sselog1")
9341    (set_attr "prefix_data16" "1")
9342    (set_attr "prefix_extra" "1")
9343    (set_attr "prefix" "maybe_vex")
9344    (set_attr "mode" "<sseinsnmode>")])
9345
9346 (define_insn "abs<mode>2"
9347   [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
9348         (abs:MMXMODEI
9349           (match_operand:MMXMODEI 1 "nonimmediate_operand" "ym")))]
9350   "TARGET_SSSE3"
9351   "pabs<mmxvecsize>\t{%1, %0|%0, %1}";
9352   [(set_attr "type" "sselog1")
9353    (set_attr "prefix_rep" "0")
9354    (set_attr "prefix_extra" "1")
9355    (set (attr "prefix_rex") (symbol_ref "x86_extended_reg_mentioned_p (insn)"))
9356    (set_attr "mode" "DI")])
9357
9358 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9359 ;;
9360 ;; AMD SSE4A instructions
9361 ;;
9362 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9363
9364 (define_insn "sse4a_movnt<mode>"
9365   [(set (match_operand:MODEF 0 "memory_operand" "=m")
9366         (unspec:MODEF
9367           [(match_operand:MODEF 1 "register_operand" "x")]
9368           UNSPEC_MOVNT))]
9369   "TARGET_SSE4A"
9370   "movnt<ssemodesuffix>\t{%1, %0|%0, %1}"
9371   [(set_attr "type" "ssemov")
9372    (set_attr "mode" "<MODE>")])
9373
9374 (define_insn "sse4a_vmmovnt<mode>"
9375   [(set (match_operand:<ssescalarmode> 0 "memory_operand" "=m")
9376         (unspec:<ssescalarmode>
9377           [(vec_select:<ssescalarmode>
9378              (match_operand:VF_128 1 "register_operand" "x")
9379              (parallel [(const_int 0)]))]
9380           UNSPEC_MOVNT))]
9381   "TARGET_SSE4A"
9382   "movnt<ssescalarmodesuffix>\t{%1, %0|%0, %1}"
9383   [(set_attr "type" "ssemov")
9384    (set_attr "mode" "<ssescalarmode>")])
9385
9386 (define_insn "sse4a_extrqi"
9387   [(set (match_operand:V2DI 0 "register_operand" "=x")
9388         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
9389                       (match_operand 2 "const_0_to_255_operand" "")
9390                       (match_operand 3 "const_0_to_255_operand" "")]
9391                      UNSPEC_EXTRQI))]
9392   "TARGET_SSE4A"
9393   "extrq\t{%3, %2, %0|%0, %2, %3}"
9394   [(set_attr "type" "sse")
9395    (set_attr "prefix_data16" "1")
9396    (set_attr "length_immediate" "2")
9397    (set_attr "mode" "TI")])
9398
9399 (define_insn "sse4a_extrq"
9400   [(set (match_operand:V2DI 0 "register_operand" "=x")
9401         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
9402                       (match_operand:V16QI 2 "register_operand" "x")]
9403                      UNSPEC_EXTRQ))]
9404   "TARGET_SSE4A"
9405   "extrq\t{%2, %0|%0, %2}"
9406   [(set_attr "type" "sse")
9407    (set_attr "prefix_data16" "1")
9408    (set_attr "mode" "TI")])
9409
9410 (define_insn "sse4a_insertqi"
9411   [(set (match_operand:V2DI 0 "register_operand" "=x")
9412         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
9413                       (match_operand:V2DI 2 "register_operand" "x")
9414                       (match_operand 3 "const_0_to_255_operand" "")
9415                       (match_operand 4 "const_0_to_255_operand" "")]
9416                      UNSPEC_INSERTQI))]
9417   "TARGET_SSE4A"
9418   "insertq\t{%4, %3, %2, %0|%0, %2, %3, %4}"
9419   [(set_attr "type" "sseins")
9420    (set_attr "prefix_data16" "0")
9421    (set_attr "prefix_rep" "1")
9422    (set_attr "length_immediate" "2")
9423    (set_attr "mode" "TI")])
9424
9425 (define_insn "sse4a_insertq"
9426   [(set (match_operand:V2DI 0 "register_operand" "=x")
9427         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0")
9428                       (match_operand:V2DI 2 "register_operand" "x")]
9429                      UNSPEC_INSERTQ))]
9430   "TARGET_SSE4A"
9431   "insertq\t{%2, %0|%0, %2}"
9432   [(set_attr "type" "sseins")
9433    (set_attr "prefix_data16" "0")
9434    (set_attr "prefix_rep" "1")
9435    (set_attr "mode" "TI")])
9436
9437 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9438 ;;
9439 ;; Intel SSE4.1 instructions
9440 ;;
9441 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9442
9443 (define_insn "<sse4_1>_blend<ssemodesuffix><avxsizesuffix>"
9444   [(set (match_operand:VF 0 "register_operand" "=x,x")
9445         (vec_merge:VF
9446           (match_operand:VF 2 "nonimmediate_operand" "xm,xm")
9447           (match_operand:VF 1 "register_operand" "0,x")
9448           (match_operand:SI 3 "const_0_to_<blendbits>_operand" "")))]
9449   "TARGET_SSE4_1"
9450   "@
9451    blend<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
9452    vblend<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9453   [(set_attr "isa" "noavx,avx")
9454    (set_attr "type" "ssemov")
9455    (set_attr "length_immediate" "1")
9456    (set_attr "prefix_data16" "1,*")
9457    (set_attr "prefix_extra" "1")
9458    (set_attr "prefix" "orig,vex")
9459    (set_attr "mode" "<MODE>")])
9460
9461 (define_insn "<sse4_1>_blendv<ssemodesuffix><avxsizesuffix>"
9462   [(set (match_operand:VF 0 "reg_not_xmm0_operand_maybe_avx" "=x,x")
9463         (unspec:VF
9464           [(match_operand:VF 1 "reg_not_xmm0_operand_maybe_avx" "0,x")
9465            (match_operand:VF 2 "nonimm_not_xmm0_operand_maybe_avx" "xm,xm")
9466            (match_operand:VF 3 "register_operand" "Yz,x")]
9467           UNSPEC_BLENDV))]
9468   "TARGET_SSE4_1"
9469   "@
9470    blendv<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
9471    vblendv<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9472   [(set_attr "isa" "noavx,avx")
9473    (set_attr "type" "ssemov")
9474    (set_attr "length_immediate" "1")
9475    (set_attr "prefix_data16" "1,*")
9476    (set_attr "prefix_extra" "1")
9477    (set_attr "prefix" "orig,vex")
9478    (set_attr "mode" "<MODE>")])
9479
9480 (define_insn "<sse4_1>_dp<ssemodesuffix><avxsizesuffix>"
9481   [(set (match_operand:VF 0 "register_operand" "=x,x")
9482         (unspec:VF
9483           [(match_operand:VF 1 "nonimmediate_operand" "%0,x")
9484            (match_operand:VF 2 "nonimmediate_operand" "xm,xm")
9485            (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
9486           UNSPEC_DP))]
9487   "TARGET_SSE4_1"
9488   "@
9489    dp<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}
9490    vdp<ssemodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9491   [(set_attr "isa" "noavx,avx")
9492    (set_attr "type" "ssemul")
9493    (set_attr "length_immediate" "1")
9494    (set_attr "prefix_data16" "1,*")
9495    (set_attr "prefix_extra" "1")
9496    (set_attr "prefix" "orig,vex")
9497    (set_attr "mode" "<MODE>")])
9498
9499 (define_insn "<sse4_1_avx2>_movntdqa"
9500   [(set (match_operand:VI8_AVX2 0 "register_operand" "=x")
9501         (unspec:VI8_AVX2 [(match_operand:VI8_AVX2 1 "memory_operand" "m")]
9502                      UNSPEC_MOVNTDQA))]
9503   "TARGET_SSE4_1"
9504   "%vmovntdqa\t{%1, %0|%0, %1}"
9505   [(set_attr "type" "ssemov")
9506    (set_attr "prefix_extra" "1")
9507    (set_attr "prefix" "maybe_vex")
9508    (set_attr "mode" "<sseinsnmode>")])
9509
9510 (define_insn "<sse4_1_avx2>_mpsadbw"
9511   [(set (match_operand:VI1_AVX2 0 "register_operand" "=x,x")
9512         (unspec:VI1_AVX2 [(match_operand:VI1_AVX2 1 "register_operand" "0,x")
9513                           (match_operand:VI1_AVX2 2 "nonimmediate_operand" "xm,xm")
9514                           (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
9515                          UNSPEC_MPSADBW))]
9516   "TARGET_SSE4_1"
9517   "@
9518    mpsadbw\t{%3, %2, %0|%0, %2, %3}
9519    vmpsadbw\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9520   [(set_attr "isa" "noavx,avx")
9521    (set_attr "type" "sselog1")
9522    (set_attr "length_immediate" "1")
9523    (set_attr "prefix_extra" "1")
9524    (set_attr "prefix" "orig,vex")
9525    (set_attr "mode" "<sseinsnmode>")])
9526
9527 (define_insn "avx2_packusdw"
9528   [(set (match_operand:V16HI 0 "register_operand" "=x")
9529         (vec_concat:V16HI
9530           (us_truncate:V8HI
9531             (match_operand:V8SI 1 "register_operand" "x"))
9532           (us_truncate:V8HI
9533             (match_operand:V8SI 2 "nonimmediate_operand" "xm"))))]
9534   "TARGET_AVX2"
9535   "vpackusdw\t{%2, %1, %0|%0, %1, %2}"
9536   [(set_attr "type" "sselog")
9537    (set_attr "prefix_extra" "1")
9538    (set_attr "prefix" "vex")
9539    (set_attr "mode" "OI")])
9540
9541 (define_insn "sse4_1_packusdw"
9542   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
9543         (vec_concat:V8HI
9544           (us_truncate:V4HI
9545             (match_operand:V4SI 1 "register_operand" "0,x"))
9546           (us_truncate:V4HI
9547             (match_operand:V4SI 2 "nonimmediate_operand" "xm,xm"))))]
9548   "TARGET_SSE4_1"
9549   "@
9550    packusdw\t{%2, %0|%0, %2}
9551    vpackusdw\t{%2, %1, %0|%0, %1, %2}"
9552   [(set_attr "isa" "noavx,avx")
9553    (set_attr "type" "sselog")
9554    (set_attr "prefix_extra" "1")
9555    (set_attr "prefix" "orig,vex")
9556    (set_attr "mode" "TI")])
9557
9558 (define_insn "<sse4_1_avx2>_pblendvb"
9559   [(set (match_operand:VI1_AVX2 0 "reg_not_xmm0_operand" "=x,x")
9560         (unspec:VI1_AVX2
9561           [(match_operand:VI1_AVX2 1 "reg_not_xmm0_operand_maybe_avx"  "0,x")
9562            (match_operand:VI1_AVX2 2 "nonimm_not_xmm0_operand_maybe_avx" "xm,xm")
9563            (match_operand:VI1_AVX2 3 "register_operand" "Yz,x")]
9564           UNSPEC_BLENDV))]
9565   "TARGET_SSE4_1"
9566   "@
9567    pblendvb\t{%3, %2, %0|%0, %2, %3}
9568    vpblendvb\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9569   [(set_attr "isa" "noavx,avx")
9570    (set_attr "type" "ssemov")
9571    (set_attr "prefix_extra" "1")
9572    (set_attr "length_immediate" "*,1")
9573    (set_attr "prefix" "orig,vex")
9574    (set_attr "mode" "<sseinsnmode>")])
9575
9576 (define_insn "sse4_1_pblendw"
9577   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
9578         (vec_merge:V8HI
9579           (match_operand:V8HI 2 "nonimmediate_operand" "xm,xm")
9580           (match_operand:V8HI 1 "register_operand" "0,x")
9581           (match_operand:SI 3 "const_0_to_255_operand" "n,n")))]
9582   "TARGET_SSE4_1"
9583   "@
9584    pblendw\t{%3, %2, %0|%0, %2, %3}
9585    vpblendw\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9586   [(set_attr "isa" "noavx,avx")
9587    (set_attr "type" "ssemov")
9588    (set_attr "prefix_extra" "1")
9589    (set_attr "length_immediate" "1")
9590    (set_attr "prefix" "orig,vex")
9591    (set_attr "mode" "TI")])
9592
9593 ;; The builtin uses an 8-bit immediate.  Expand that.
9594 (define_expand "avx2_pblendw"
9595   [(set (match_operand:V16HI 0 "register_operand" "")
9596         (vec_merge:V16HI
9597           (match_operand:V16HI 2 "nonimmediate_operand" "")
9598           (match_operand:V16HI 1 "register_operand" "")
9599           (match_operand:SI 3 "const_0_to_255_operand" "")))]
9600   "TARGET_AVX2"
9601 {
9602   HOST_WIDE_INT val = INTVAL (operands[3]) & 0xff;
9603   operands[3] = GEN_INT (val << 8 | val);
9604 })
9605
9606 (define_insn "*avx2_pblendw"
9607   [(set (match_operand:V16HI 0 "register_operand" "=x")
9608         (vec_merge:V16HI
9609           (match_operand:V16HI 2 "nonimmediate_operand" "xm")
9610           (match_operand:V16HI 1 "register_operand" "x")
9611           (match_operand:SI 3 "avx2_pblendw_operand" "n")))]
9612   "TARGET_AVX2"
9613 {
9614   operands[3] = GEN_INT (INTVAL (operands[3]) & 0xff);
9615   return "vpblendw\t{%3, %2, %1, %0|%0, %1, %2, %3}";
9616 }
9617   [(set_attr "type" "ssemov")
9618    (set_attr "prefix_extra" "1")
9619    (set_attr "length_immediate" "1")
9620    (set_attr "prefix" "vex")
9621    (set_attr "mode" "OI")])
9622
9623 (define_insn "avx2_pblendd<mode>"
9624   [(set (match_operand:VI4_AVX2 0 "register_operand" "=x")
9625         (vec_merge:VI4_AVX2
9626           (match_operand:VI4_AVX2 2 "nonimmediate_operand" "xm")
9627           (match_operand:VI4_AVX2 1 "register_operand" "x")
9628           (match_operand:SI 3 "const_0_to_255_operand" "n")))]
9629   "TARGET_AVX2"
9630   "vpblendd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9631   [(set_attr "type" "ssemov")
9632    (set_attr "prefix_extra" "1")
9633    (set_attr "length_immediate" "1")
9634    (set_attr "prefix" "vex")
9635    (set_attr "mode" "<sseinsnmode>")])
9636
9637 (define_insn "sse4_1_phminposuw"
9638   [(set (match_operand:V8HI 0 "register_operand" "=x")
9639         (unspec:V8HI [(match_operand:V8HI 1 "nonimmediate_operand" "xm")]
9640                      UNSPEC_PHMINPOSUW))]
9641   "TARGET_SSE4_1"
9642   "%vphminposuw\t{%1, %0|%0, %1}"
9643   [(set_attr "type" "sselog1")
9644    (set_attr "prefix_extra" "1")
9645    (set_attr "prefix" "maybe_vex")
9646    (set_attr "mode" "TI")])
9647
9648 (define_insn "avx2_<code>v16qiv16hi2"
9649   [(set (match_operand:V16HI 0 "register_operand" "=x")
9650         (any_extend:V16HI
9651           (match_operand:V16QI 1 "nonimmediate_operand" "xm")))]
9652   "TARGET_AVX2"
9653   "vpmov<extsuffix>bw\t{%1, %0|%0, %1}"
9654   [(set_attr "type" "ssemov")
9655    (set_attr "prefix_extra" "1")
9656    (set_attr "prefix" "vex")
9657    (set_attr "mode" "OI")])
9658
9659 (define_insn "sse4_1_<code>v8qiv8hi2"
9660   [(set (match_operand:V8HI 0 "register_operand" "=x")
9661         (any_extend:V8HI
9662           (vec_select:V8QI
9663             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9664             (parallel [(const_int 0)
9665                        (const_int 1)
9666                        (const_int 2)
9667                        (const_int 3)
9668                        (const_int 4)
9669                        (const_int 5)
9670                        (const_int 6)
9671                        (const_int 7)]))))]
9672   "TARGET_SSE4_1"
9673   "%vpmov<extsuffix>bw\t{%1, %0|%0, %q1}"
9674   [(set_attr "type" "ssemov")
9675    (set_attr "prefix_extra" "1")
9676    (set_attr "prefix" "maybe_vex")
9677    (set_attr "mode" "TI")])
9678
9679 (define_insn "avx2_<code>v8qiv8si2"
9680   [(set (match_operand:V8SI 0 "register_operand" "=x")
9681         (any_extend:V8SI
9682           (vec_select:V8QI
9683             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9684             (parallel [(const_int 0)
9685                        (const_int 1)
9686                        (const_int 2)
9687                        (const_int 3)
9688                        (const_int 4)
9689                        (const_int 5)
9690                        (const_int 6)
9691                        (const_int 7)]))))]
9692   "TARGET_AVX2"
9693   "vpmov<extsuffix>bd\t{%1, %0|%0, %q1}"
9694   [(set_attr "type" "ssemov")
9695    (set_attr "prefix_extra" "1")
9696    (set_attr "prefix" "vex")
9697    (set_attr "mode" "OI")])
9698
9699 (define_insn "sse4_1_<code>v4qiv4si2"
9700   [(set (match_operand:V4SI 0 "register_operand" "=x")
9701         (any_extend:V4SI
9702           (vec_select:V4QI
9703             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9704             (parallel [(const_int 0)
9705                        (const_int 1)
9706                        (const_int 2)
9707                        (const_int 3)]))))]
9708   "TARGET_SSE4_1"
9709   "%vpmov<extsuffix>bd\t{%1, %0|%0, %k1}"
9710   [(set_attr "type" "ssemov")
9711    (set_attr "prefix_extra" "1")
9712    (set_attr "prefix" "maybe_vex")
9713    (set_attr "mode" "TI")])
9714
9715 (define_insn "avx2_<code>v8hiv8si2"
9716   [(set (match_operand:V8SI 0 "register_operand" "=x")
9717         (any_extend:V8SI
9718             (match_operand:V8HI 1 "nonimmediate_operand" "xm")))]
9719   "TARGET_AVX2"
9720   "vpmov<extsuffix>wd\t{%1, %0|%0, %1}"
9721   [(set_attr "type" "ssemov")
9722    (set_attr "prefix_extra" "1")
9723    (set_attr "prefix" "vex")
9724    (set_attr "mode" "OI")])
9725
9726 (define_insn "sse4_1_<code>v4hiv4si2"
9727   [(set (match_operand:V4SI 0 "register_operand" "=x")
9728         (any_extend:V4SI
9729           (vec_select:V4HI
9730             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9731             (parallel [(const_int 0)
9732                        (const_int 1)
9733                        (const_int 2)
9734                        (const_int 3)]))))]
9735   "TARGET_SSE4_1"
9736   "%vpmov<extsuffix>wd\t{%1, %0|%0, %q1}"
9737   [(set_attr "type" "ssemov")
9738    (set_attr "prefix_extra" "1")
9739    (set_attr "prefix" "maybe_vex")
9740    (set_attr "mode" "TI")])
9741
9742 (define_insn "avx2_<code>v4qiv4di2"
9743   [(set (match_operand:V4DI 0 "register_operand" "=x")
9744         (any_extend:V4DI
9745           (vec_select:V4QI
9746             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9747             (parallel [(const_int 0)
9748                        (const_int 1)
9749                        (const_int 2)
9750                        (const_int 3)]))))]
9751   "TARGET_AVX2"
9752   "vpmov<extsuffix>bq\t{%1, %0|%0, %k1}"
9753   [(set_attr "type" "ssemov")
9754    (set_attr "prefix_extra" "1")
9755    (set_attr "prefix" "vex")
9756    (set_attr "mode" "OI")])
9757
9758 (define_insn "sse4_1_<code>v2qiv2di2"
9759   [(set (match_operand:V2DI 0 "register_operand" "=x")
9760         (any_extend:V2DI
9761           (vec_select:V2QI
9762             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
9763             (parallel [(const_int 0)
9764                        (const_int 1)]))))]
9765   "TARGET_SSE4_1"
9766   "%vpmov<extsuffix>bq\t{%1, %0|%0, %w1}"
9767   [(set_attr "type" "ssemov")
9768    (set_attr "prefix_extra" "1")
9769    (set_attr "prefix" "maybe_vex")
9770    (set_attr "mode" "TI")])
9771
9772 (define_insn "avx2_<code>v4hiv4di2"
9773   [(set (match_operand:V4DI 0 "register_operand" "=x")
9774         (any_extend:V4DI
9775           (vec_select:V4HI
9776             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9777             (parallel [(const_int 0)
9778                        (const_int 1)
9779                        (const_int 2)
9780                        (const_int 3)]))))]
9781   "TARGET_AVX2"
9782   "vpmov<extsuffix>wq\t{%1, %0|%0, %q1}"
9783   [(set_attr "type" "ssemov")
9784    (set_attr "prefix_extra" "1")
9785    (set_attr "prefix" "vex")
9786    (set_attr "mode" "OI")])
9787
9788 (define_insn "sse4_1_<code>v2hiv2di2"
9789   [(set (match_operand:V2DI 0 "register_operand" "=x")
9790         (any_extend:V2DI
9791           (vec_select:V2HI
9792             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
9793             (parallel [(const_int 0)
9794                        (const_int 1)]))))]
9795   "TARGET_SSE4_1"
9796   "%vpmov<extsuffix>wq\t{%1, %0|%0, %k1}"
9797   [(set_attr "type" "ssemov")
9798    (set_attr "prefix_extra" "1")
9799    (set_attr "prefix" "maybe_vex")
9800    (set_attr "mode" "TI")])
9801
9802 (define_insn "avx2_<code>v4siv4di2"
9803   [(set (match_operand:V4DI 0 "register_operand" "=x")
9804         (any_extend:V4DI
9805             (match_operand:V4SI 1 "nonimmediate_operand" "xm")))]
9806   "TARGET_AVX2"
9807   "vpmov<extsuffix>dq\t{%1, %0|%0, %1}"
9808   [(set_attr "type" "ssemov")
9809    (set_attr "prefix_extra" "1")
9810    (set_attr "mode" "OI")])
9811
9812 (define_insn "sse4_1_<code>v2siv2di2"
9813   [(set (match_operand:V2DI 0 "register_operand" "=x")
9814         (any_extend:V2DI
9815           (vec_select:V2SI
9816             (match_operand:V4SI 1 "nonimmediate_operand" "xm")
9817             (parallel [(const_int 0)
9818                        (const_int 1)]))))]
9819   "TARGET_SSE4_1"
9820   "%vpmov<extsuffix>dq\t{%1, %0|%0, %q1}"
9821   [(set_attr "type" "ssemov")
9822    (set_attr "prefix_extra" "1")
9823    (set_attr "prefix" "maybe_vex")
9824    (set_attr "mode" "TI")])
9825
9826 ;; ptestps/ptestpd are very similar to comiss and ucomiss when
9827 ;; setting FLAGS_REG. But it is not a really compare instruction.
9828 (define_insn "avx_vtest<ssemodesuffix><avxsizesuffix>"
9829   [(set (reg:CC FLAGS_REG)
9830         (unspec:CC [(match_operand:VF 0 "register_operand" "x")
9831                     (match_operand:VF 1 "nonimmediate_operand" "xm")]
9832                    UNSPEC_VTESTP))]
9833   "TARGET_AVX"
9834   "vtest<ssemodesuffix>\t{%1, %0|%0, %1}"
9835   [(set_attr "type" "ssecomi")
9836    (set_attr "prefix_extra" "1")
9837    (set_attr "prefix" "vex")
9838    (set_attr "mode" "<MODE>")])
9839
9840 ;; ptest is very similar to comiss and ucomiss when setting FLAGS_REG.
9841 ;; But it is not a really compare instruction.
9842 (define_insn "avx_ptest256"
9843   [(set (reg:CC FLAGS_REG)
9844         (unspec:CC [(match_operand:V4DI 0 "register_operand" "x")
9845                     (match_operand:V4DI 1 "nonimmediate_operand" "xm")]
9846                    UNSPEC_PTEST))]
9847   "TARGET_AVX"
9848   "vptest\t{%1, %0|%0, %1}"
9849   [(set_attr "type" "ssecomi")
9850    (set_attr "prefix_extra" "1")
9851    (set_attr "prefix" "vex")
9852    (set_attr "mode" "OI")])
9853
9854 (define_insn "sse4_1_ptest"
9855   [(set (reg:CC FLAGS_REG)
9856         (unspec:CC [(match_operand:V2DI 0 "register_operand" "x")
9857                     (match_operand:V2DI 1 "nonimmediate_operand" "xm")]
9858                    UNSPEC_PTEST))]
9859   "TARGET_SSE4_1"
9860   "%vptest\t{%1, %0|%0, %1}"
9861   [(set_attr "type" "ssecomi")
9862    (set_attr "prefix_extra" "1")
9863    (set_attr "prefix" "maybe_vex")
9864    (set_attr "mode" "TI")])
9865
9866 (define_insn "<sse4_1>_round<ssemodesuffix><avxsizesuffix>"
9867   [(set (match_operand:VF 0 "register_operand" "=x")
9868         (unspec:VF
9869           [(match_operand:VF 1 "nonimmediate_operand" "xm")
9870            (match_operand:SI 2 "const_0_to_15_operand" "n")]
9871           UNSPEC_ROUND))]
9872   "TARGET_ROUND"
9873   "%vround<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
9874   [(set_attr "type" "ssecvt")
9875    (set (attr "prefix_data16")
9876      (if_then_else
9877        (match_test "TARGET_AVX")
9878      (const_string "*")
9879      (const_string "1")))
9880    (set_attr "prefix_extra" "1")
9881    (set_attr "length_immediate" "1")
9882    (set_attr "prefix" "maybe_vex")
9883    (set_attr "mode" "<MODE>")])
9884
9885 (define_insn "sse4_1_round<ssescalarmodesuffix>"
9886   [(set (match_operand:VF_128 0 "register_operand" "=x,x")
9887         (vec_merge:VF_128
9888           (unspec:VF_128
9889             [(match_operand:VF_128 2 "register_operand" "x,x")
9890              (match_operand:SI 3 "const_0_to_15_operand" "n,n")]
9891             UNSPEC_ROUND)
9892           (match_operand:VF_128 1 "register_operand" "0,x")
9893           (const_int 1)))]
9894   "TARGET_ROUND"
9895   "@
9896    round<ssescalarmodesuffix>\t{%3, %2, %0|%0, %2, %3}
9897    vround<ssescalarmodesuffix>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
9898   [(set_attr "isa" "noavx,avx")
9899    (set_attr "type" "ssecvt")
9900    (set_attr "length_immediate" "1")
9901    (set_attr "prefix_data16" "1,*")
9902    (set_attr "prefix_extra" "1")
9903    (set_attr "prefix" "orig,vex")
9904    (set_attr "mode" "<MODE>")])
9905
9906 (define_expand "round<mode>2"
9907   [(set (match_dup 4)
9908         (plus:VF
9909           (match_operand:VF 1 "nonimmediate_operand" "")
9910           (match_dup 3)))
9911    (set (match_operand:VF 0 "register_operand" "")
9912         (unspec:VF
9913           [(match_dup 4) (match_dup 5)]
9914           UNSPEC_ROUND))]
9915   "TARGET_ROUND && !flag_trapping_math"
9916 {
9917   enum machine_mode scalar_mode;
9918   const struct real_format *fmt;
9919   REAL_VALUE_TYPE pred_half, half_minus_pred_half;
9920   rtx half, vec_half;
9921
9922   scalar_mode = GET_MODE_INNER (<MODE>mode);
9923
9924   /* load nextafter (0.5, 0.0) */
9925   fmt = REAL_MODE_FORMAT (scalar_mode);
9926   real_2expN (&half_minus_pred_half, -(fmt->p) - 1, scalar_mode);
9927   REAL_ARITHMETIC (pred_half, MINUS_EXPR, dconsthalf, half_minus_pred_half);
9928   half = const_double_from_real_value (pred_half, scalar_mode);
9929
9930   vec_half = ix86_build_const_vector (<MODE>mode, true, half);
9931   vec_half = force_reg (<MODE>mode, vec_half);
9932
9933   operands[3] = gen_reg_rtx (<MODE>mode);
9934   emit_insn (gen_copysign<mode>3 (operands[3], vec_half, operands[1]));
9935
9936   operands[4] = gen_reg_rtx (<MODE>mode);
9937   operands[5] = GEN_INT (ROUND_TRUNC);
9938 })
9939
9940 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9941 ;;
9942 ;; Intel SSE4.2 string/text processing instructions
9943 ;;
9944 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9945
9946 (define_insn_and_split "sse4_2_pcmpestr"
9947   [(set (match_operand:SI 0 "register_operand" "=c,c")
9948         (unspec:SI
9949           [(match_operand:V16QI 2 "reg_not_xmm0_operand" "x,x")
9950            (match_operand:SI 3 "register_operand" "a,a")
9951            (match_operand:V16QI 4 "nonimm_not_xmm0_operand" "x,m")
9952            (match_operand:SI 5 "register_operand" "d,d")
9953            (match_operand:SI 6 "const_0_to_255_operand" "n,n")]
9954           UNSPEC_PCMPESTR))
9955    (set (match_operand:V16QI 1 "register_operand" "=Yz,Yz")
9956         (unspec:V16QI
9957           [(match_dup 2)
9958            (match_dup 3)
9959            (match_dup 4)
9960            (match_dup 5)
9961            (match_dup 6)]
9962           UNSPEC_PCMPESTR))
9963    (set (reg:CC FLAGS_REG)
9964         (unspec:CC
9965           [(match_dup 2)
9966            (match_dup 3)
9967            (match_dup 4)
9968            (match_dup 5)
9969            (match_dup 6)]
9970           UNSPEC_PCMPESTR))]
9971   "TARGET_SSE4_2
9972    && can_create_pseudo_p ()"
9973   "#"
9974   "&& 1"
9975   [(const_int 0)]
9976 {
9977   int ecx = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[0]));
9978   int xmm0 = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[1]));
9979   int flags = !find_regno_note (curr_insn, REG_UNUSED, FLAGS_REG);
9980
9981   if (ecx)
9982     emit_insn (gen_sse4_2_pcmpestri (operands[0], operands[2],
9983                                      operands[3], operands[4],
9984                                      operands[5], operands[6]));
9985   if (xmm0)
9986     emit_insn (gen_sse4_2_pcmpestrm (operands[1], operands[2],
9987                                      operands[3], operands[4],
9988                                      operands[5], operands[6]));
9989   if (flags && !(ecx || xmm0))
9990     emit_insn (gen_sse4_2_pcmpestr_cconly (NULL, NULL,
9991                                            operands[2], operands[3],
9992                                            operands[4], operands[5],
9993                                            operands[6]));
9994   if (!(flags || ecx || xmm0))
9995     emit_note (NOTE_INSN_DELETED);
9996
9997   DONE;
9998 }
9999   [(set_attr "type" "sselog")
10000    (set_attr "prefix_data16" "1")
10001    (set_attr "prefix_extra" "1")
10002    (set_attr "length_immediate" "1")
10003    (set_attr "memory" "none,load")
10004    (set_attr "mode" "TI")])
10005
10006 (define_insn "sse4_2_pcmpestri"
10007   [(set (match_operand:SI 0 "register_operand" "=c,c")
10008         (unspec:SI
10009           [(match_operand:V16QI 1 "register_operand" "x,x")
10010            (match_operand:SI 2 "register_operand" "a,a")
10011            (match_operand:V16QI 3 "nonimmediate_operand" "x,m")
10012            (match_operand:SI 4 "register_operand" "d,d")
10013            (match_operand:SI 5 "const_0_to_255_operand" "n,n")]
10014           UNSPEC_PCMPESTR))
10015    (set (reg:CC FLAGS_REG)
10016         (unspec:CC
10017           [(match_dup 1)
10018            (match_dup 2)
10019            (match_dup 3)
10020            (match_dup 4)
10021            (match_dup 5)]
10022           UNSPEC_PCMPESTR))]
10023   "TARGET_SSE4_2"
10024   "%vpcmpestri\t{%5, %3, %1|%1, %3, %5}"
10025   [(set_attr "type" "sselog")
10026    (set_attr "prefix_data16" "1")
10027    (set_attr "prefix_extra" "1")
10028    (set_attr "prefix" "maybe_vex")
10029    (set_attr "length_immediate" "1")
10030    (set_attr "memory" "none,load")
10031    (set_attr "mode" "TI")])
10032
10033 (define_insn "sse4_2_pcmpestrm"
10034   [(set (match_operand:V16QI 0 "register_operand" "=Yz,Yz")
10035         (unspec:V16QI
10036           [(match_operand:V16QI 1 "register_operand" "x,x")
10037            (match_operand:SI 2 "register_operand" "a,a")
10038            (match_operand:V16QI 3 "nonimmediate_operand" "x,m")
10039            (match_operand:SI 4 "register_operand" "d,d")
10040            (match_operand:SI 5 "const_0_to_255_operand" "n,n")]
10041           UNSPEC_PCMPESTR))
10042    (set (reg:CC FLAGS_REG)
10043         (unspec:CC
10044           [(match_dup 1)
10045            (match_dup 2)
10046            (match_dup 3)
10047            (match_dup 4)
10048            (match_dup 5)]
10049           UNSPEC_PCMPESTR))]
10050   "TARGET_SSE4_2"
10051   "%vpcmpestrm\t{%5, %3, %1|%1, %3, %5}"
10052   [(set_attr "type" "sselog")
10053    (set_attr "prefix_data16" "1")
10054    (set_attr "prefix_extra" "1")
10055    (set_attr "length_immediate" "1")
10056    (set_attr "prefix" "maybe_vex")
10057    (set_attr "memory" "none,load")
10058    (set_attr "mode" "TI")])
10059
10060 (define_insn "sse4_2_pcmpestr_cconly"
10061   [(set (reg:CC FLAGS_REG)
10062         (unspec:CC
10063           [(match_operand:V16QI 2 "register_operand" "x,x,x,x")
10064            (match_operand:SI 3 "register_operand" "a,a,a,a")
10065            (match_operand:V16QI 4 "nonimmediate_operand" "x,m,x,m")
10066            (match_operand:SI 5 "register_operand" "d,d,d,d")
10067            (match_operand:SI 6 "const_0_to_255_operand" "n,n,n,n")]
10068           UNSPEC_PCMPESTR))
10069    (clobber (match_scratch:V16QI 0 "=Yz,Yz,X,X"))
10070    (clobber (match_scratch:SI    1 "= X, X,c,c"))]
10071   "TARGET_SSE4_2"
10072   "@
10073    %vpcmpestrm\t{%6, %4, %2|%2, %4, %6}
10074    %vpcmpestrm\t{%6, %4, %2|%2, %4, %6}
10075    %vpcmpestri\t{%6, %4, %2|%2, %4, %6}
10076    %vpcmpestri\t{%6, %4, %2|%2, %4, %6}"
10077   [(set_attr "type" "sselog")
10078    (set_attr "prefix_data16" "1")
10079    (set_attr "prefix_extra" "1")
10080    (set_attr "length_immediate" "1")
10081    (set_attr "memory" "none,load,none,load")
10082    (set_attr "prefix" "maybe_vex")
10083    (set_attr "mode" "TI")])
10084
10085 (define_insn_and_split "sse4_2_pcmpistr"
10086   [(set (match_operand:SI 0 "register_operand" "=c,c")
10087         (unspec:SI
10088           [(match_operand:V16QI 2 "reg_not_xmm0_operand" "x,x")
10089            (match_operand:V16QI 3 "nonimm_not_xmm0_operand" "x,m")
10090            (match_operand:SI 4 "const_0_to_255_operand" "n,n")]
10091           UNSPEC_PCMPISTR))
10092    (set (match_operand:V16QI 1 "register_operand" "=Yz,Yz")
10093         (unspec:V16QI
10094           [(match_dup 2)
10095            (match_dup 3)
10096            (match_dup 4)]
10097           UNSPEC_PCMPISTR))
10098    (set (reg:CC FLAGS_REG)
10099         (unspec:CC
10100           [(match_dup 2)
10101            (match_dup 3)
10102            (match_dup 4)]
10103           UNSPEC_PCMPISTR))]
10104   "TARGET_SSE4_2
10105    && can_create_pseudo_p ()"
10106   "#"
10107   "&& 1"
10108   [(const_int 0)]
10109 {
10110   int ecx = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[0]));
10111   int xmm0 = !find_regno_note (curr_insn, REG_UNUSED, REGNO (operands[1]));
10112   int flags = !find_regno_note (curr_insn, REG_UNUSED, FLAGS_REG);
10113
10114   if (ecx)
10115     emit_insn (gen_sse4_2_pcmpistri (operands[0], operands[2],
10116                                      operands[3], operands[4]));
10117   if (xmm0)
10118     emit_insn (gen_sse4_2_pcmpistrm (operands[1], operands[2],
10119                                      operands[3], operands[4]));
10120   if (flags && !(ecx || xmm0))
10121     emit_insn (gen_sse4_2_pcmpistr_cconly (NULL, NULL,
10122                                            operands[2], operands[3],
10123                                            operands[4]));
10124   if (!(flags || ecx || xmm0))
10125     emit_note (NOTE_INSN_DELETED);
10126
10127   DONE;
10128 }
10129   [(set_attr "type" "sselog")
10130    (set_attr "prefix_data16" "1")
10131    (set_attr "prefix_extra" "1")
10132    (set_attr "length_immediate" "1")
10133    (set_attr "memory" "none,load")
10134    (set_attr "mode" "TI")])
10135
10136 (define_insn "sse4_2_pcmpistri"
10137   [(set (match_operand:SI 0 "register_operand" "=c,c")
10138         (unspec:SI
10139           [(match_operand:V16QI 1 "register_operand" "x,x")
10140            (match_operand:V16QI 2 "nonimmediate_operand" "x,m")
10141            (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
10142           UNSPEC_PCMPISTR))
10143    (set (reg:CC FLAGS_REG)
10144         (unspec:CC
10145           [(match_dup 1)
10146            (match_dup 2)
10147            (match_dup 3)]
10148           UNSPEC_PCMPISTR))]
10149   "TARGET_SSE4_2"
10150   "%vpcmpistri\t{%3, %2, %1|%1, %2, %3}"
10151   [(set_attr "type" "sselog")
10152    (set_attr "prefix_data16" "1")
10153    (set_attr "prefix_extra" "1")
10154    (set_attr "length_immediate" "1")
10155    (set_attr "prefix" "maybe_vex")
10156    (set_attr "memory" "none,load")
10157    (set_attr "mode" "TI")])
10158
10159 (define_insn "sse4_2_pcmpistrm"
10160   [(set (match_operand:V16QI 0 "register_operand" "=Yz,Yz")
10161         (unspec:V16QI
10162           [(match_operand:V16QI 1 "register_operand" "x,x")
10163            (match_operand:V16QI 2 "nonimmediate_operand" "x,m")
10164            (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
10165           UNSPEC_PCMPISTR))
10166    (set (reg:CC FLAGS_REG)
10167         (unspec:CC
10168           [(match_dup 1)
10169            (match_dup 2)
10170            (match_dup 3)]
10171           UNSPEC_PCMPISTR))]
10172   "TARGET_SSE4_2"
10173   "%vpcmpistrm\t{%3, %2, %1|%1, %2, %3}"
10174   [(set_attr "type" "sselog")
10175    (set_attr "prefix_data16" "1")
10176    (set_attr "prefix_extra" "1")
10177    (set_attr "length_immediate" "1")
10178    (set_attr "prefix" "maybe_vex")
10179    (set_attr "memory" "none,load")
10180    (set_attr "mode" "TI")])
10181
10182 (define_insn "sse4_2_pcmpistr_cconly"
10183   [(set (reg:CC FLAGS_REG)
10184         (unspec:CC
10185           [(match_operand:V16QI 2 "register_operand" "x,x,x,x")
10186            (match_operand:V16QI 3 "nonimmediate_operand" "x,m,x,m")
10187            (match_operand:SI 4 "const_0_to_255_operand" "n,n,n,n")]
10188           UNSPEC_PCMPISTR))
10189    (clobber (match_scratch:V16QI 0 "=Yz,Yz,X,X"))
10190    (clobber (match_scratch:SI    1 "= X, X,c,c"))]
10191   "TARGET_SSE4_2"
10192   "@
10193    %vpcmpistrm\t{%4, %3, %2|%2, %3, %4}
10194    %vpcmpistrm\t{%4, %3, %2|%2, %3, %4}
10195    %vpcmpistri\t{%4, %3, %2|%2, %3, %4}
10196    %vpcmpistri\t{%4, %3, %2|%2, %3, %4}"
10197   [(set_attr "type" "sselog")
10198    (set_attr "prefix_data16" "1")
10199    (set_attr "prefix_extra" "1")
10200    (set_attr "length_immediate" "1")
10201    (set_attr "memory" "none,load,none,load")
10202    (set_attr "prefix" "maybe_vex")
10203    (set_attr "mode" "TI")])
10204
10205 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
10206 ;;
10207 ;; XOP instructions
10208 ;;
10209 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
10210
10211 ;; XOP parallel integer multiply/add instructions.
10212 ;; Note the XOP multiply/add instructions
10213 ;;     a[i] = b[i] * c[i] + d[i];
10214 ;; do not allow the value being added to be a memory operation.
10215 (define_insn "xop_pmacsww"
10216   [(set (match_operand:V8HI 0 "register_operand" "=x")
10217         (plus:V8HI
10218          (mult:V8HI
10219           (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10220           (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
10221          (match_operand:V8HI 3 "nonimmediate_operand" "x")))]
10222   "TARGET_XOP"
10223   "vpmacsww\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10224   [(set_attr "type" "ssemuladd")
10225    (set_attr "mode" "TI")])
10226
10227 (define_insn "xop_pmacssww"
10228   [(set (match_operand:V8HI 0 "register_operand" "=x")
10229         (ss_plus:V8HI
10230          (mult:V8HI (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10231                     (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
10232          (match_operand:V8HI 3 "nonimmediate_operand" "x")))]
10233   "TARGET_XOP"
10234   "vpmacssww\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10235   [(set_attr "type" "ssemuladd")
10236    (set_attr "mode" "TI")])
10237
10238 (define_insn "xop_pmacsdd"
10239   [(set (match_operand:V4SI 0 "register_operand" "=x")
10240         (plus:V4SI
10241          (mult:V4SI
10242           (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10243           (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
10244          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10245   "TARGET_XOP"
10246   "vpmacsdd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10247   [(set_attr "type" "ssemuladd")
10248    (set_attr "mode" "TI")])
10249
10250 (define_insn "xop_pmacssdd"
10251   [(set (match_operand:V4SI 0 "register_operand" "=x")
10252         (ss_plus:V4SI
10253          (mult:V4SI (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10254                     (match_operand:V4SI 2 "nonimmediate_operand" "xm"))
10255          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10256   "TARGET_XOP"
10257   "vpmacssdd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10258   [(set_attr "type" "ssemuladd")
10259    (set_attr "mode" "TI")])
10260
10261 (define_insn "xop_pmacssdql"
10262   [(set (match_operand:V2DI 0 "register_operand" "=x")
10263         (ss_plus:V2DI
10264          (mult:V2DI
10265           (sign_extend:V2DI
10266            (vec_select:V2SI
10267             (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10268             (parallel [(const_int 1)
10269                        (const_int 3)])))
10270           (vec_select:V2SI
10271            (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10272            (parallel [(const_int 1)
10273                       (const_int 3)])))
10274          (match_operand:V2DI 3 "nonimmediate_operand" "x")))]
10275   "TARGET_XOP"
10276   "vpmacssdql\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10277   [(set_attr "type" "ssemuladd")
10278    (set_attr "mode" "TI")])
10279
10280 (define_insn "xop_pmacssdqh"
10281   [(set (match_operand:V2DI 0 "register_operand" "=x")
10282         (ss_plus:V2DI
10283          (mult:V2DI
10284           (sign_extend:V2DI
10285            (vec_select:V2SI
10286             (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10287             (parallel [(const_int 0)
10288                        (const_int 2)])))
10289           (sign_extend:V2DI
10290            (vec_select:V2SI
10291             (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10292             (parallel [(const_int 0)
10293                        (const_int 2)]))))
10294          (match_operand:V2DI 3 "nonimmediate_operand" "x")))]
10295   "TARGET_XOP"
10296   "vpmacssdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10297   [(set_attr "type" "ssemuladd")
10298    (set_attr "mode" "TI")])
10299
10300 (define_insn "xop_pmacsdql"
10301   [(set (match_operand:V2DI 0 "register_operand" "=x")
10302         (plus:V2DI
10303          (mult:V2DI
10304           (sign_extend:V2DI
10305            (vec_select:V2SI
10306             (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10307             (parallel [(const_int 1)
10308                        (const_int 3)])))
10309           (sign_extend:V2DI
10310            (vec_select:V2SI
10311             (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10312             (parallel [(const_int 1)
10313                        (const_int 3)]))))
10314          (match_operand:V2DI 3 "nonimmediate_operand" "x")))]
10315   "TARGET_XOP"
10316   "vpmacsdql\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10317   [(set_attr "type" "ssemuladd")
10318    (set_attr "mode" "TI")])
10319
10320 ;; We don't have a straight 32-bit parallel multiply and extend on XOP, so
10321 ;; fake it with a multiply/add.  In general, we expect the define_split to
10322 ;; occur before register allocation, so we have to handle the corner case where
10323 ;; the target is the same as operands 1/2
10324 (define_insn_and_split "xop_mulv2div2di3_low"
10325   [(set (match_operand:V2DI 0 "register_operand" "=&x")
10326         (mult:V2DI
10327           (sign_extend:V2DI
10328             (vec_select:V2SI
10329               (match_operand:V4SI 1 "register_operand" "%x")
10330               (parallel [(const_int 1)
10331                          (const_int 3)])))
10332           (sign_extend:V2DI
10333             (vec_select:V2SI
10334               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10335               (parallel [(const_int 1)
10336                          (const_int 3)])))))]
10337   "TARGET_XOP"
10338   "#"
10339   "&& reload_completed"
10340   [(set (match_dup 0)
10341         (match_dup 3))
10342    (set (match_dup 0)
10343         (plus:V2DI
10344          (mult:V2DI
10345           (sign_extend:V2DI
10346            (vec_select:V2SI
10347             (match_dup 1)
10348             (parallel [(const_int 1)
10349                        (const_int 3)])))
10350           (sign_extend:V2DI
10351            (vec_select:V2SI
10352             (match_dup 2)
10353             (parallel [(const_int 1)
10354                        (const_int 3)]))))
10355          (match_dup 0)))]
10356 {
10357   operands[3] = CONST0_RTX (V2DImode);
10358 }
10359   [(set_attr "type" "ssemul")
10360    (set_attr "mode" "TI")])
10361
10362 (define_insn "xop_pmacsdqh"
10363   [(set (match_operand:V2DI 0 "register_operand" "=x")
10364         (plus:V2DI
10365          (mult:V2DI
10366           (sign_extend:V2DI
10367            (vec_select:V2SI
10368             (match_operand:V4SI 1 "nonimmediate_operand" "%x")
10369             (parallel [(const_int 0)
10370                        (const_int 2)])))
10371           (sign_extend:V2DI
10372            (vec_select:V2SI
10373             (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10374             (parallel [(const_int 0)
10375                        (const_int 2)]))))
10376          (match_operand:V2DI 3 "nonimmediate_operand" "x")))]
10377   "TARGET_XOP"
10378   "vpmacsdqh\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10379   [(set_attr "type" "ssemuladd")
10380    (set_attr "mode" "TI")])
10381
10382 ;; We don't have a straight 32-bit parallel multiply and extend on XOP, so
10383 ;; fake it with a multiply/add.  In general, we expect the define_split to
10384 ;; occur before register allocation, so we have to handle the corner case where
10385 ;; the target is the same as either operands[1] or operands[2]
10386 (define_insn_and_split "xop_mulv2div2di3_high"
10387   [(set (match_operand:V2DI 0 "register_operand" "=&x")
10388         (mult:V2DI
10389           (sign_extend:V2DI
10390             (vec_select:V2SI
10391               (match_operand:V4SI 1 "register_operand" "%x")
10392               (parallel [(const_int 0)
10393                          (const_int 2)])))
10394           (sign_extend:V2DI
10395             (vec_select:V2SI
10396               (match_operand:V4SI 2 "nonimmediate_operand" "xm")
10397               (parallel [(const_int 0)
10398                          (const_int 2)])))))]
10399   "TARGET_XOP"
10400   "#"
10401   "&& reload_completed"
10402   [(set (match_dup 0)
10403         (match_dup 3))
10404    (set (match_dup 0)
10405         (plus:V2DI
10406          (mult:V2DI
10407           (sign_extend:V2DI
10408            (vec_select:V2SI
10409             (match_dup 1)
10410             (parallel [(const_int 0)
10411                        (const_int 2)])))
10412           (sign_extend:V2DI
10413            (vec_select:V2SI
10414             (match_dup 2)
10415             (parallel [(const_int 0)
10416                        (const_int 2)]))))
10417          (match_dup 0)))]
10418 {
10419   operands[3] = CONST0_RTX (V2DImode);
10420 }
10421   [(set_attr "type" "ssemul")
10422    (set_attr "mode" "TI")])
10423
10424 ;; XOP parallel integer multiply/add instructions for the intrinisics
10425 (define_insn "xop_pmacsswd"
10426   [(set (match_operand:V4SI 0 "register_operand" "=x")
10427         (ss_plus:V4SI
10428          (mult:V4SI
10429           (sign_extend:V4SI
10430            (vec_select:V4HI
10431             (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10432             (parallel [(const_int 1)
10433                        (const_int 3)
10434                        (const_int 5)
10435                        (const_int 7)])))
10436           (sign_extend:V4SI
10437            (vec_select:V4HI
10438             (match_operand:V8HI 2 "nonimmediate_operand" "xm")
10439             (parallel [(const_int 1)
10440                        (const_int 3)
10441                        (const_int 5)
10442                        (const_int 7)]))))
10443          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10444   "TARGET_XOP"
10445   "vpmacsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10446   [(set_attr "type" "ssemuladd")
10447    (set_attr "mode" "TI")])
10448
10449 (define_insn "xop_pmacswd"
10450   [(set (match_operand:V4SI 0 "register_operand" "=x")
10451         (plus:V4SI
10452          (mult:V4SI
10453           (sign_extend:V4SI
10454            (vec_select:V4HI
10455             (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10456             (parallel [(const_int 1)
10457                        (const_int 3)
10458                        (const_int 5)
10459                        (const_int 7)])))
10460           (sign_extend:V4SI
10461            (vec_select:V4HI
10462             (match_operand:V8HI 2 "nonimmediate_operand" "xm")
10463             (parallel [(const_int 1)
10464                        (const_int 3)
10465                        (const_int 5)
10466                        (const_int 7)]))))
10467          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10468   "TARGET_XOP"
10469   "vpmacswd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10470   [(set_attr "type" "ssemuladd")
10471    (set_attr "mode" "TI")])
10472
10473 (define_insn "xop_pmadcsswd"
10474   [(set (match_operand:V4SI 0 "register_operand" "=x")
10475         (ss_plus:V4SI
10476          (plus:V4SI
10477           (mult:V4SI
10478            (sign_extend:V4SI
10479             (vec_select:V4HI
10480              (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10481              (parallel [(const_int 0)
10482                         (const_int 2)
10483                         (const_int 4)
10484                         (const_int 6)])))
10485            (sign_extend:V4SI
10486             (vec_select:V4HI
10487              (match_operand:V8HI 2 "nonimmediate_operand" "xm")
10488              (parallel [(const_int 0)
10489                         (const_int 2)
10490                         (const_int 4)
10491                         (const_int 6)]))))
10492           (mult:V4SI
10493            (sign_extend:V4SI
10494             (vec_select:V4HI
10495              (match_dup 1)
10496              (parallel [(const_int 1)
10497                         (const_int 3)
10498                         (const_int 5)
10499                         (const_int 7)])))
10500            (sign_extend:V4SI
10501             (vec_select:V4HI
10502              (match_dup 2)
10503              (parallel [(const_int 1)
10504                         (const_int 3)
10505                         (const_int 5)
10506                         (const_int 7)])))))
10507          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10508   "TARGET_XOP"
10509   "vpmadcsswd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10510   [(set_attr "type" "ssemuladd")
10511    (set_attr "mode" "TI")])
10512
10513 (define_insn "xop_pmadcswd"
10514   [(set (match_operand:V4SI 0 "register_operand" "=x")
10515         (plus:V4SI
10516          (plus:V4SI
10517           (mult:V4SI
10518            (sign_extend:V4SI
10519             (vec_select:V4HI
10520              (match_operand:V8HI 1 "nonimmediate_operand" "%x")
10521              (parallel [(const_int 0)
10522                         (const_int 2)
10523                         (const_int 4)
10524                         (const_int 6)])))
10525            (sign_extend:V4SI
10526             (vec_select:V4HI
10527              (match_operand:V8HI 2 "nonimmediate_operand" "xm")
10528              (parallel [(const_int 0)
10529                         (const_int 2)
10530                         (const_int 4)
10531                         (const_int 6)]))))
10532           (mult:V4SI
10533            (sign_extend:V4SI
10534             (vec_select:V4HI
10535              (match_dup 1)
10536              (parallel [(const_int 1)
10537                         (const_int 3)
10538                         (const_int 5)
10539                         (const_int 7)])))
10540            (sign_extend:V4SI
10541             (vec_select:V4HI
10542              (match_dup 2)
10543              (parallel [(const_int 1)
10544                         (const_int 3)
10545                         (const_int 5)
10546                         (const_int 7)])))))
10547          (match_operand:V4SI 3 "nonimmediate_operand" "x")))]
10548   "TARGET_XOP"
10549   "vpmadcswd\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10550   [(set_attr "type" "ssemuladd")
10551    (set_attr "mode" "TI")])
10552
10553 ;; XOP parallel XMM conditional moves
10554 (define_insn "xop_pcmov_<mode><avxsizesuffix>"
10555   [(set (match_operand:V 0 "register_operand" "=x,x")
10556         (if_then_else:V
10557           (match_operand:V 3 "nonimmediate_operand" "x,m")
10558           (match_operand:V 1 "register_operand" "x,x")
10559           (match_operand:V 2 "nonimmediate_operand" "xm,x")))]
10560   "TARGET_XOP"
10561   "vpcmov\t{%3, %2, %1, %0|%0, %1, %2, %3}"
10562   [(set_attr "type" "sse4arg")])
10563
10564 ;; XOP horizontal add/subtract instructions
10565 (define_insn "xop_phaddbw"
10566   [(set (match_operand:V8HI 0 "register_operand" "=x")
10567         (plus:V8HI
10568          (sign_extend:V8HI
10569           (vec_select:V8QI
10570            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10571            (parallel [(const_int 0)
10572                       (const_int 2)
10573                       (const_int 4)
10574                       (const_int 6)
10575                       (const_int 8)
10576                       (const_int 10)
10577                       (const_int 12)
10578                       (const_int 14)])))
10579          (sign_extend:V8HI
10580           (vec_select:V8QI
10581            (match_dup 1)
10582            (parallel [(const_int 1)
10583                       (const_int 3)
10584                       (const_int 5)
10585                       (const_int 7)
10586                       (const_int 9)
10587                       (const_int 11)
10588                       (const_int 13)
10589                       (const_int 15)])))))]
10590   "TARGET_XOP"
10591   "vphaddbw\t{%1, %0|%0, %1}"
10592   [(set_attr "type" "sseiadd1")])
10593
10594 (define_insn "xop_phaddbd"
10595   [(set (match_operand:V4SI 0 "register_operand" "=x")
10596         (plus:V4SI
10597          (plus:V4SI
10598           (sign_extend:V4SI
10599            (vec_select:V4QI
10600             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10601             (parallel [(const_int 0)
10602                        (const_int 4)
10603                        (const_int 8)
10604                        (const_int 12)])))
10605           (sign_extend:V4SI
10606            (vec_select:V4QI
10607             (match_dup 1)
10608             (parallel [(const_int 1)
10609                        (const_int 5)
10610                        (const_int 9)
10611                        (const_int 13)]))))
10612          (plus:V4SI
10613           (sign_extend:V4SI
10614            (vec_select:V4QI
10615             (match_dup 1)
10616             (parallel [(const_int 2)
10617                        (const_int 6)
10618                        (const_int 10)
10619                        (const_int 14)])))
10620           (sign_extend:V4SI
10621            (vec_select:V4QI
10622             (match_dup 1)
10623             (parallel [(const_int 3)
10624                        (const_int 7)
10625                        (const_int 11)
10626                        (const_int 15)]))))))]
10627   "TARGET_XOP"
10628   "vphaddbd\t{%1, %0|%0, %1}"
10629   [(set_attr "type" "sseiadd1")])
10630
10631 (define_insn "xop_phaddbq"
10632   [(set (match_operand:V2DI 0 "register_operand" "=x")
10633         (plus:V2DI
10634          (plus:V2DI
10635           (plus:V2DI
10636            (sign_extend:V2DI
10637             (vec_select:V2QI
10638              (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10639              (parallel [(const_int 0)
10640                         (const_int 4)])))
10641            (sign_extend:V2DI
10642             (vec_select:V2QI
10643              (match_dup 1)
10644              (parallel [(const_int 1)
10645                         (const_int 5)]))))
10646           (plus:V2DI
10647            (sign_extend:V2DI
10648             (vec_select:V2QI
10649              (match_dup 1)
10650              (parallel [(const_int 2)
10651                         (const_int 6)])))
10652            (sign_extend:V2DI
10653             (vec_select:V2QI
10654              (match_dup 1)
10655              (parallel [(const_int 3)
10656                         (const_int 7)])))))
10657          (plus:V2DI
10658           (plus:V2DI
10659            (sign_extend:V2DI
10660             (vec_select:V2QI
10661              (match_dup 1)
10662              (parallel [(const_int 8)
10663                         (const_int 12)])))
10664            (sign_extend:V2DI
10665             (vec_select:V2QI
10666              (match_dup 1)
10667              (parallel [(const_int 9)
10668                         (const_int 13)]))))
10669           (plus:V2DI
10670            (sign_extend:V2DI
10671             (vec_select:V2QI
10672              (match_dup 1)
10673              (parallel [(const_int 10)
10674                         (const_int 14)])))
10675            (sign_extend:V2DI
10676             (vec_select:V2QI
10677              (match_dup 1)
10678              (parallel [(const_int 11)
10679                         (const_int 15)])))))))]
10680   "TARGET_XOP"
10681   "vphaddbq\t{%1, %0|%0, %1}"
10682   [(set_attr "type" "sseiadd1")])
10683
10684 (define_insn "xop_phaddwd"
10685   [(set (match_operand:V4SI 0 "register_operand" "=x")
10686         (plus:V4SI
10687          (sign_extend:V4SI
10688           (vec_select:V4HI
10689            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10690            (parallel [(const_int 0)
10691                       (const_int 2)
10692                       (const_int 4)
10693                       (const_int 6)])))
10694          (sign_extend:V4SI
10695           (vec_select:V4HI
10696            (match_dup 1)
10697            (parallel [(const_int 1)
10698                       (const_int 3)
10699                       (const_int 5)
10700                       (const_int 7)])))))]
10701   "TARGET_XOP"
10702   "vphaddwd\t{%1, %0|%0, %1}"
10703   [(set_attr "type" "sseiadd1")])
10704
10705 (define_insn "xop_phaddwq"
10706   [(set (match_operand:V2DI 0 "register_operand" "=x")
10707         (plus:V2DI
10708          (plus:V2DI
10709           (sign_extend:V2DI
10710            (vec_select:V2HI
10711             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10712             (parallel [(const_int 0)
10713                        (const_int 4)])))
10714           (sign_extend:V2DI
10715            (vec_select:V2HI
10716             (match_dup 1)
10717             (parallel [(const_int 1)
10718                        (const_int 5)]))))
10719          (plus:V2DI
10720           (sign_extend:V2DI
10721            (vec_select:V2HI
10722             (match_dup 1)
10723             (parallel [(const_int 2)
10724                        (const_int 6)])))
10725           (sign_extend:V2DI
10726            (vec_select:V2HI
10727             (match_dup 1)
10728             (parallel [(const_int 3)
10729                        (const_int 7)]))))))]
10730   "TARGET_XOP"
10731   "vphaddwq\t{%1, %0|%0, %1}"
10732   [(set_attr "type" "sseiadd1")])
10733
10734 (define_insn "xop_phadddq"
10735   [(set (match_operand:V2DI 0 "register_operand" "=x")
10736         (plus:V2DI
10737          (sign_extend:V2DI
10738           (vec_select:V2SI
10739            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10740            (parallel [(const_int 0)
10741                       (const_int 2)])))
10742          (sign_extend:V2DI
10743           (vec_select:V2SI
10744            (match_dup 1)
10745            (parallel [(const_int 1)
10746                       (const_int 3)])))))]
10747   "TARGET_XOP"
10748   "vphadddq\t{%1, %0|%0, %1}"
10749   [(set_attr "type" "sseiadd1")])
10750
10751 (define_insn "xop_phaddubw"
10752   [(set (match_operand:V8HI 0 "register_operand" "=x")
10753         (plus:V8HI
10754          (zero_extend:V8HI
10755           (vec_select:V8QI
10756            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10757            (parallel [(const_int 0)
10758                       (const_int 2)
10759                       (const_int 4)
10760                       (const_int 6)
10761                       (const_int 8)
10762                       (const_int 10)
10763                       (const_int 12)
10764                       (const_int 14)])))
10765          (zero_extend:V8HI
10766           (vec_select:V8QI
10767            (match_dup 1)
10768            (parallel [(const_int 1)
10769                       (const_int 3)
10770                       (const_int 5)
10771                       (const_int 7)
10772                       (const_int 9)
10773                       (const_int 11)
10774                       (const_int 13)
10775                       (const_int 15)])))))]
10776   "TARGET_XOP"
10777   "vphaddubw\t{%1, %0|%0, %1}"
10778   [(set_attr "type" "sseiadd1")])
10779
10780 (define_insn "xop_phaddubd"
10781   [(set (match_operand:V4SI 0 "register_operand" "=x")
10782         (plus:V4SI
10783          (plus:V4SI
10784           (zero_extend:V4SI
10785            (vec_select:V4QI
10786             (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10787             (parallel [(const_int 0)
10788                        (const_int 4)
10789                        (const_int 8)
10790                        (const_int 12)])))
10791           (zero_extend:V4SI
10792            (vec_select:V4QI
10793             (match_dup 1)
10794             (parallel [(const_int 1)
10795                        (const_int 5)
10796                        (const_int 9)
10797                        (const_int 13)]))))
10798          (plus:V4SI
10799           (zero_extend:V4SI
10800            (vec_select:V4QI
10801             (match_dup 1)
10802             (parallel [(const_int 2)
10803                        (const_int 6)
10804                        (const_int 10)
10805                        (const_int 14)])))
10806           (zero_extend:V4SI
10807            (vec_select:V4QI
10808             (match_dup 1)
10809             (parallel [(const_int 3)
10810                        (const_int 7)
10811                        (const_int 11)
10812                        (const_int 15)]))))))]
10813   "TARGET_XOP"
10814   "vphaddubd\t{%1, %0|%0, %1}"
10815   [(set_attr "type" "sseiadd1")])
10816
10817 (define_insn "xop_phaddubq"
10818   [(set (match_operand:V2DI 0 "register_operand" "=x")
10819         (plus:V2DI
10820          (plus:V2DI
10821           (plus:V2DI
10822            (zero_extend:V2DI
10823             (vec_select:V2QI
10824              (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10825              (parallel [(const_int 0)
10826                         (const_int 4)])))
10827            (sign_extend:V2DI
10828             (vec_select:V2QI
10829              (match_dup 1)
10830              (parallel [(const_int 1)
10831                         (const_int 5)]))))
10832           (plus:V2DI
10833            (zero_extend:V2DI
10834             (vec_select:V2QI
10835              (match_dup 1)
10836              (parallel [(const_int 2)
10837                         (const_int 6)])))
10838            (zero_extend:V2DI
10839             (vec_select:V2QI
10840              (match_dup 1)
10841              (parallel [(const_int 3)
10842                         (const_int 7)])))))
10843          (plus:V2DI
10844           (plus:V2DI
10845            (zero_extend:V2DI
10846             (vec_select:V2QI
10847              (match_dup 1)
10848              (parallel [(const_int 8)
10849                         (const_int 12)])))
10850            (sign_extend:V2DI
10851             (vec_select:V2QI
10852              (match_dup 1)
10853              (parallel [(const_int 9)
10854                         (const_int 13)]))))
10855           (plus:V2DI
10856            (zero_extend:V2DI
10857             (vec_select:V2QI
10858              (match_dup 1)
10859              (parallel [(const_int 10)
10860                         (const_int 14)])))
10861            (zero_extend:V2DI
10862             (vec_select:V2QI
10863              (match_dup 1)
10864              (parallel [(const_int 11)
10865                         (const_int 15)])))))))]
10866   "TARGET_XOP"
10867   "vphaddubq\t{%1, %0|%0, %1}"
10868   [(set_attr "type" "sseiadd1")])
10869
10870 (define_insn "xop_phadduwd"
10871   [(set (match_operand:V4SI 0 "register_operand" "=x")
10872         (plus:V4SI
10873          (zero_extend:V4SI
10874           (vec_select:V4HI
10875            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10876            (parallel [(const_int 0)
10877                       (const_int 2)
10878                       (const_int 4)
10879                       (const_int 6)])))
10880          (zero_extend:V4SI
10881           (vec_select:V4HI
10882            (match_dup 1)
10883            (parallel [(const_int 1)
10884                       (const_int 3)
10885                       (const_int 5)
10886                       (const_int 7)])))))]
10887   "TARGET_XOP"
10888   "vphadduwd\t{%1, %0|%0, %1}"
10889   [(set_attr "type" "sseiadd1")])
10890
10891 (define_insn "xop_phadduwq"
10892   [(set (match_operand:V2DI 0 "register_operand" "=x")
10893         (plus:V2DI
10894          (plus:V2DI
10895           (zero_extend:V2DI
10896            (vec_select:V2HI
10897             (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10898             (parallel [(const_int 0)
10899                        (const_int 4)])))
10900           (zero_extend:V2DI
10901            (vec_select:V2HI
10902             (match_dup 1)
10903             (parallel [(const_int 1)
10904                        (const_int 5)]))))
10905          (plus:V2DI
10906           (zero_extend:V2DI
10907            (vec_select:V2HI
10908             (match_dup 1)
10909             (parallel [(const_int 2)
10910                        (const_int 6)])))
10911           (zero_extend:V2DI
10912            (vec_select:V2HI
10913             (match_dup 1)
10914             (parallel [(const_int 3)
10915                        (const_int 7)]))))))]
10916   "TARGET_XOP"
10917   "vphadduwq\t{%1, %0|%0, %1}"
10918   [(set_attr "type" "sseiadd1")])
10919
10920 (define_insn "xop_phaddudq"
10921   [(set (match_operand:V2DI 0 "register_operand" "=x")
10922         (plus:V2DI
10923          (zero_extend:V2DI
10924           (vec_select:V2SI
10925            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10926            (parallel [(const_int 0)
10927                       (const_int 2)])))
10928          (zero_extend:V2DI
10929           (vec_select:V2SI
10930            (match_dup 1)
10931            (parallel [(const_int 1)
10932                       (const_int 3)])))))]
10933   "TARGET_XOP"
10934   "vphaddudq\t{%1, %0|%0, %1}"
10935   [(set_attr "type" "sseiadd1")])
10936
10937 (define_insn "xop_phsubbw"
10938   [(set (match_operand:V8HI 0 "register_operand" "=x")
10939         (minus:V8HI
10940          (sign_extend:V8HI
10941           (vec_select:V8QI
10942            (match_operand:V16QI 1 "nonimmediate_operand" "xm")
10943            (parallel [(const_int 0)
10944                       (const_int 2)
10945                       (const_int 4)
10946                       (const_int 6)
10947                       (const_int 8)
10948                       (const_int 10)
10949                       (const_int 12)
10950                       (const_int 14)])))
10951          (sign_extend:V8HI
10952           (vec_select:V8QI
10953            (match_dup 1)
10954            (parallel [(const_int 1)
10955                       (const_int 3)
10956                       (const_int 5)
10957                       (const_int 7)
10958                       (const_int 9)
10959                       (const_int 11)
10960                       (const_int 13)
10961                       (const_int 15)])))))]
10962   "TARGET_XOP"
10963   "vphsubbw\t{%1, %0|%0, %1}"
10964   [(set_attr "type" "sseiadd1")])
10965
10966 (define_insn "xop_phsubwd"
10967   [(set (match_operand:V4SI 0 "register_operand" "=x")
10968         (minus:V4SI
10969          (sign_extend:V4SI
10970           (vec_select:V4HI
10971            (match_operand:V8HI 1 "nonimmediate_operand" "xm")
10972            (parallel [(const_int 0)
10973                       (const_int 2)
10974                       (const_int 4)
10975                       (const_int 6)])))
10976          (sign_extend:V4SI
10977           (vec_select:V4HI
10978            (match_dup 1)
10979            (parallel [(const_int 1)
10980                       (const_int 3)
10981                       (const_int 5)
10982                       (const_int 7)])))))]
10983   "TARGET_XOP"
10984   "vphsubwd\t{%1, %0|%0, %1}"
10985   [(set_attr "type" "sseiadd1")])
10986
10987 (define_insn "xop_phsubdq"
10988   [(set (match_operand:V2DI 0 "register_operand" "=x")
10989         (minus:V2DI
10990          (sign_extend:V2DI
10991           (vec_select:V2SI
10992            (match_operand:V4SI 1 "nonimmediate_operand" "xm")
10993            (parallel [(const_int 0)
10994                       (const_int 2)])))
10995          (sign_extend:V2DI
10996           (vec_select:V2SI
10997            (match_dup 1)
10998            (parallel [(const_int 1)
10999                       (const_int 3)])))))]
11000   "TARGET_XOP"
11001   "vphsubdq\t{%1, %0|%0, %1}"
11002   [(set_attr "type" "sseiadd1")])
11003
11004 ;; XOP permute instructions
11005 (define_insn "xop_pperm"
11006   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
11007         (unspec:V16QI
11008           [(match_operand:V16QI 1 "register_operand" "x,x")
11009            (match_operand:V16QI 2 "nonimmediate_operand" "x,m")
11010            (match_operand:V16QI 3 "nonimmediate_operand" "xm,x")]
11011           UNSPEC_XOP_PERMUTE))]
11012   "TARGET_XOP && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
11013   "vpperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11014   [(set_attr "type" "sse4arg")
11015    (set_attr "mode" "TI")])
11016
11017 ;; XOP pack instructions that combine two vectors into a smaller vector
11018 (define_insn "xop_pperm_pack_v2di_v4si"
11019   [(set (match_operand:V4SI 0 "register_operand" "=x,x")
11020         (vec_concat:V4SI
11021          (truncate:V2SI
11022           (match_operand:V2DI 1 "register_operand" "x,x"))
11023          (truncate:V2SI
11024           (match_operand:V2DI 2 "nonimmediate_operand" "x,m"))))
11025    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x"))]
11026   "TARGET_XOP && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
11027   "vpperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11028   [(set_attr "type" "sse4arg")
11029    (set_attr "mode" "TI")])
11030
11031 (define_insn "xop_pperm_pack_v4si_v8hi"
11032   [(set (match_operand:V8HI 0 "register_operand" "=x,x")
11033         (vec_concat:V8HI
11034          (truncate:V4HI
11035           (match_operand:V4SI 1 "register_operand" "x,x"))
11036          (truncate:V4HI
11037           (match_operand:V4SI 2 "nonimmediate_operand" "x,m"))))
11038    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x"))]
11039   "TARGET_XOP && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
11040   "vpperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11041   [(set_attr "type" "sse4arg")
11042    (set_attr "mode" "TI")])
11043
11044 (define_insn "xop_pperm_pack_v8hi_v16qi"
11045   [(set (match_operand:V16QI 0 "register_operand" "=x,x")
11046         (vec_concat:V16QI
11047          (truncate:V8QI
11048           (match_operand:V8HI 1 "register_operand" "x,x"))
11049          (truncate:V8QI
11050           (match_operand:V8HI 2 "nonimmediate_operand" "x,m"))))
11051    (use (match_operand:V16QI 3 "nonimmediate_operand" "xm,x"))]
11052   "TARGET_XOP && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
11053   "vpperm\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11054   [(set_attr "type" "sse4arg")
11055    (set_attr "mode" "TI")])
11056
11057 ;; XOP packed rotate instructions
11058 (define_expand "rotl<mode>3"
11059   [(set (match_operand:VI_128 0 "register_operand" "")
11060         (rotate:VI_128
11061          (match_operand:VI_128 1 "nonimmediate_operand" "")
11062          (match_operand:SI 2 "general_operand")))]
11063   "TARGET_XOP"
11064 {
11065   /* If we were given a scalar, convert it to parallel */
11066   if (! const_0_to_<sserotatemax>_operand (operands[2], SImode))
11067     {
11068       rtvec vs = rtvec_alloc (<ssescalarnum>);
11069       rtx par = gen_rtx_PARALLEL (<MODE>mode, vs);
11070       rtx reg = gen_reg_rtx (<MODE>mode);
11071       rtx op2 = operands[2];
11072       int i;
11073
11074       if (GET_MODE (op2) != <ssescalarmode>mode)
11075         {
11076           op2 = gen_reg_rtx (<ssescalarmode>mode);
11077           convert_move (op2, operands[2], false);
11078         }
11079
11080       for (i = 0; i < <ssescalarnum>; i++)
11081         RTVEC_ELT (vs, i) = op2;
11082
11083       emit_insn (gen_vec_init<mode> (reg, par));
11084       emit_insn (gen_xop_vrotl<mode>3 (operands[0], operands[1], reg));
11085       DONE;
11086     }
11087 })
11088
11089 (define_expand "rotr<mode>3"
11090   [(set (match_operand:VI_128 0 "register_operand" "")
11091         (rotatert:VI_128
11092          (match_operand:VI_128 1 "nonimmediate_operand" "")
11093          (match_operand:SI 2 "general_operand")))]
11094   "TARGET_XOP"
11095 {
11096   /* If we were given a scalar, convert it to parallel */
11097   if (! const_0_to_<sserotatemax>_operand (operands[2], SImode))
11098     {
11099       rtvec vs = rtvec_alloc (<ssescalarnum>);
11100       rtx par = gen_rtx_PARALLEL (<MODE>mode, vs);
11101       rtx neg = gen_reg_rtx (<MODE>mode);
11102       rtx reg = gen_reg_rtx (<MODE>mode);
11103       rtx op2 = operands[2];
11104       int i;
11105
11106       if (GET_MODE (op2) != <ssescalarmode>mode)
11107         {
11108           op2 = gen_reg_rtx (<ssescalarmode>mode);
11109           convert_move (op2, operands[2], false);
11110         }
11111
11112       for (i = 0; i < <ssescalarnum>; i++)
11113         RTVEC_ELT (vs, i) = op2;
11114
11115       emit_insn (gen_vec_init<mode> (reg, par));
11116       emit_insn (gen_neg<mode>2 (neg, reg));
11117       emit_insn (gen_xop_vrotl<mode>3 (operands[0], operands[1], neg));
11118       DONE;
11119     }
11120 })
11121
11122 (define_insn "xop_rotl<mode>3"
11123   [(set (match_operand:VI_128 0 "register_operand" "=x")
11124         (rotate:VI_128
11125          (match_operand:VI_128 1 "nonimmediate_operand" "xm")
11126          (match_operand:SI 2 "const_0_to_<sserotatemax>_operand" "n")))]
11127   "TARGET_XOP"
11128   "vprot<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11129   [(set_attr "type" "sseishft")
11130    (set_attr "length_immediate" "1")
11131    (set_attr "mode" "TI")])
11132
11133 (define_insn "xop_rotr<mode>3"
11134   [(set (match_operand:VI_128 0 "register_operand" "=x")
11135         (rotatert:VI_128
11136          (match_operand:VI_128 1 "nonimmediate_operand" "xm")
11137          (match_operand:SI 2 "const_0_to_<sserotatemax>_operand" "n")))]
11138   "TARGET_XOP"
11139 {
11140   operands[3] = GEN_INT ((<ssescalarnum> * 8) - INTVAL (operands[2]));
11141   return \"vprot<ssemodesuffix>\t{%3, %1, %0|%0, %1, %3}\";
11142 }
11143   [(set_attr "type" "sseishft")
11144    (set_attr "length_immediate" "1")
11145    (set_attr "mode" "TI")])
11146
11147 (define_expand "vrotr<mode>3"
11148   [(match_operand:VI_128 0 "register_operand" "")
11149    (match_operand:VI_128 1 "register_operand" "")
11150    (match_operand:VI_128 2 "register_operand" "")]
11151   "TARGET_XOP"
11152 {
11153   rtx reg = gen_reg_rtx (<MODE>mode);
11154   emit_insn (gen_neg<mode>2 (reg, operands[2]));
11155   emit_insn (gen_xop_vrotl<mode>3 (operands[0], operands[1], reg));
11156   DONE;
11157 })
11158
11159 (define_expand "vrotl<mode>3"
11160   [(match_operand:VI_128 0 "register_operand" "")
11161    (match_operand:VI_128 1 "register_operand" "")
11162    (match_operand:VI_128 2 "register_operand" "")]
11163   "TARGET_XOP"
11164 {
11165   emit_insn (gen_xop_vrotl<mode>3 (operands[0], operands[1], operands[2]));
11166   DONE;
11167 })
11168
11169 (define_insn "xop_vrotl<mode>3"
11170   [(set (match_operand:VI_128 0 "register_operand" "=x,x")
11171         (if_then_else:VI_128
11172          (ge:VI_128
11173           (match_operand:VI_128 2 "nonimmediate_operand" "x,m")
11174           (const_int 0))
11175          (rotate:VI_128
11176           (match_operand:VI_128 1 "nonimmediate_operand" "xm,x")
11177           (match_dup 2))
11178          (rotatert:VI_128
11179           (match_dup 1)
11180           (neg:VI_128 (match_dup 2)))))]
11181   "TARGET_XOP && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
11182   "vprot<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11183   [(set_attr "type" "sseishft")
11184    (set_attr "prefix_data16" "0")
11185    (set_attr "prefix_extra" "2")
11186    (set_attr "mode" "TI")])
11187
11188 ;; XOP packed shift instructions.
11189 (define_expand "vlshr<mode>3"
11190   [(set (match_operand:VI12_128 0 "register_operand" "")
11191         (lshiftrt:VI12_128
11192           (match_operand:VI12_128 1 "register_operand" "")
11193           (match_operand:VI12_128 2 "nonimmediate_operand" "")))]
11194   "TARGET_XOP"
11195 {
11196   rtx neg = gen_reg_rtx (<MODE>mode);
11197   emit_insn (gen_neg<mode>2 (neg, operands[2]));
11198   emit_insn (gen_xop_shl<mode>3 (operands[0], operands[1], neg));
11199   DONE;
11200 })
11201
11202 (define_expand "vlshr<mode>3"
11203   [(set (match_operand:VI48_128 0 "register_operand" "")
11204         (lshiftrt:VI48_128
11205           (match_operand:VI48_128 1 "register_operand" "")
11206           (match_operand:VI48_128 2 "nonimmediate_operand" "")))]
11207   "TARGET_AVX2 || TARGET_XOP"
11208 {
11209   if (!TARGET_AVX2)
11210     {
11211       rtx neg = gen_reg_rtx (<MODE>mode);
11212       emit_insn (gen_neg<mode>2 (neg, operands[2]));
11213       emit_insn (gen_xop_shl<mode>3 (operands[0], operands[1], neg));
11214       DONE;
11215     }
11216 })
11217
11218 (define_expand "vlshr<mode>3"
11219   [(set (match_operand:VI48_256 0 "register_operand" "")
11220         (lshiftrt:VI48_256
11221           (match_operand:VI48_256 1 "register_operand" "")
11222           (match_operand:VI48_256 2 "nonimmediate_operand" "")))]
11223   "TARGET_AVX2")
11224
11225 (define_expand "vashr<mode>3"
11226   [(set (match_operand:VI128_128 0 "register_operand" "")
11227         (ashiftrt:VI128_128
11228           (match_operand:VI128_128 1 "register_operand" "")
11229           (match_operand:VI128_128 2 "nonimmediate_operand" "")))]
11230   "TARGET_XOP"
11231 {
11232   rtx neg = gen_reg_rtx (<MODE>mode);
11233   emit_insn (gen_neg<mode>2 (neg, operands[2]));
11234   emit_insn (gen_xop_sha<mode>3 (operands[0], operands[1], neg));
11235   DONE;
11236 })
11237
11238 (define_expand "vashrv4si3"
11239   [(set (match_operand:V4SI 0 "register_operand" "")
11240         (ashiftrt:V4SI (match_operand:V4SI 1 "register_operand" "")
11241                        (match_operand:V4SI 2 "nonimmediate_operand" "")))]
11242   "TARGET_AVX2 || TARGET_XOP"
11243 {
11244   if (!TARGET_AVX2)
11245     {
11246       rtx neg = gen_reg_rtx (V4SImode);
11247       emit_insn (gen_negv4si2 (neg, operands[2]));
11248       emit_insn (gen_xop_shav4si3 (operands[0], operands[1], neg));
11249       DONE;
11250     }
11251 })
11252
11253 (define_expand "vashrv8si3"
11254   [(set (match_operand:V8SI 0 "register_operand" "")
11255         (ashiftrt:V8SI (match_operand:V8SI 1 "register_operand" "")
11256                        (match_operand:V8SI 2 "nonimmediate_operand" "")))]
11257   "TARGET_AVX2")
11258
11259 (define_expand "vashl<mode>3"
11260   [(set (match_operand:VI12_128 0 "register_operand" "")
11261         (ashift:VI12_128
11262           (match_operand:VI12_128 1 "register_operand" "")
11263           (match_operand:VI12_128 2 "nonimmediate_operand" "")))]
11264   "TARGET_XOP"
11265 {
11266   emit_insn (gen_xop_sha<mode>3 (operands[0], operands[1], operands[2]));
11267   DONE;
11268 })
11269
11270 (define_expand "vashl<mode>3"
11271   [(set (match_operand:VI48_128 0 "register_operand" "")
11272         (ashift:VI48_128
11273           (match_operand:VI48_128 1 "register_operand" "")
11274           (match_operand:VI48_128 2 "nonimmediate_operand" "")))]
11275   "TARGET_AVX2 || TARGET_XOP"
11276 {
11277   if (!TARGET_AVX2)
11278     {
11279       operands[2] = force_reg (<MODE>mode, operands[2]);
11280       emit_insn (gen_xop_sha<mode>3 (operands[0], operands[1], operands[2]));
11281       DONE;
11282     }
11283 })
11284
11285 (define_expand "vashl<mode>3"
11286   [(set (match_operand:VI48_256 0 "register_operand" "")
11287         (ashift:VI48_256
11288           (match_operand:VI48_256 1 "register_operand" "")
11289           (match_operand:VI48_256 2 "nonimmediate_operand" "")))]
11290   "TARGET_AVX2")
11291
11292 (define_insn "xop_sha<mode>3"
11293   [(set (match_operand:VI_128 0 "register_operand" "=x,x")
11294         (if_then_else:VI_128
11295          (ge:VI_128
11296           (match_operand:VI_128 2 "nonimmediate_operand" "x,m")
11297           (const_int 0))
11298          (ashift:VI_128
11299           (match_operand:VI_128 1 "nonimmediate_operand" "xm,x")
11300           (match_dup 2))
11301          (ashiftrt:VI_128
11302           (match_dup 1)
11303           (neg:VI_128 (match_dup 2)))))]
11304   "TARGET_XOP && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
11305   "vpsha<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11306   [(set_attr "type" "sseishft")
11307    (set_attr "prefix_data16" "0")
11308    (set_attr "prefix_extra" "2")
11309    (set_attr "mode" "TI")])
11310
11311 (define_insn "xop_shl<mode>3"
11312   [(set (match_operand:VI_128 0 "register_operand" "=x,x")
11313         (if_then_else:VI_128
11314          (ge:VI_128
11315           (match_operand:VI_128 2 "nonimmediate_operand" "x,m")
11316           (const_int 0))
11317          (ashift:VI_128
11318           (match_operand:VI_128 1 "nonimmediate_operand" "xm,x")
11319           (match_dup 2))
11320          (lshiftrt:VI_128
11321           (match_dup 1)
11322           (neg:VI_128 (match_dup 2)))))]
11323   "TARGET_XOP && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
11324   "vpshl<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11325   [(set_attr "type" "sseishft")
11326    (set_attr "prefix_data16" "0")
11327    (set_attr "prefix_extra" "2")
11328    (set_attr "mode" "TI")])
11329
11330 ;; SSE2 doesn't have some shift variants, so define versions for XOP
11331 (define_expand "ashlv16qi3"
11332   [(set (match_operand:V16QI 0 "register_operand" "")
11333         (ashift:V16QI
11334           (match_operand:V16QI 1 "register_operand" "")
11335           (match_operand:SI 2 "nonmemory_operand" "")))]
11336   "TARGET_XOP"
11337 {
11338   rtx reg = gen_reg_rtx (V16QImode);
11339   rtx par;
11340   int i;
11341
11342   par = gen_rtx_PARALLEL (V16QImode, rtvec_alloc (16));
11343   for (i = 0; i < 16; i++)
11344     XVECEXP (par, 0, i) = operands[2];
11345
11346   emit_insn (gen_vec_initv16qi (reg, par));
11347   emit_insn (gen_xop_shav16qi3 (operands[0], operands[1], reg));
11348   DONE;
11349 })
11350
11351 (define_expand "<shift_insn>v16qi3"
11352   [(set (match_operand:V16QI 0 "register_operand" "")
11353         (any_shiftrt:V16QI
11354           (match_operand:V16QI 1 "register_operand" "")
11355           (match_operand:SI 2 "nonmemory_operand" "")))]
11356   "TARGET_XOP"
11357 {
11358   rtx reg = gen_reg_rtx (V16QImode);
11359   rtx par;
11360   bool negate = false;
11361   rtx (*shift_insn)(rtx, rtx, rtx);
11362   int i;
11363
11364   if (CONST_INT_P (operands[2]))
11365     operands[2] = GEN_INT (-INTVAL (operands[2]));
11366   else
11367     negate = true;
11368
11369   par = gen_rtx_PARALLEL (V16QImode, rtvec_alloc (16));
11370   for (i = 0; i < 16; i++)
11371     XVECEXP (par, 0, i) = operands[2];
11372
11373   emit_insn (gen_vec_initv16qi (reg, par));
11374
11375   if (negate)
11376     emit_insn (gen_negv16qi2 (reg, reg));
11377
11378   if (<CODE> == LSHIFTRT)
11379     shift_insn = gen_xop_shlv16qi3;
11380   else
11381     shift_insn = gen_xop_shav16qi3;
11382
11383   emit_insn (shift_insn (operands[0], operands[1], reg));
11384   DONE;
11385 })
11386
11387 (define_expand "ashrv2di3"
11388   [(set (match_operand:V2DI 0 "register_operand" "")
11389         (ashiftrt:V2DI
11390           (match_operand:V2DI 1 "register_operand" "")
11391           (match_operand:DI 2 "nonmemory_operand" "")))]
11392   "TARGET_XOP"
11393 {
11394   rtx reg = gen_reg_rtx (V2DImode);
11395   rtx par;
11396   bool negate = false;
11397   int i;
11398
11399   if (CONST_INT_P (operands[2]))
11400     operands[2] = GEN_INT (-INTVAL (operands[2]));
11401   else
11402     negate = true;
11403
11404   par = gen_rtx_PARALLEL (V2DImode, rtvec_alloc (2));
11405   for (i = 0; i < 2; i++)
11406     XVECEXP (par, 0, i) = operands[2];
11407
11408   emit_insn (gen_vec_initv2di (reg, par));
11409
11410   if (negate)
11411     emit_insn (gen_negv2di2 (reg, reg));
11412
11413   emit_insn (gen_xop_shav2di3 (operands[0], operands[1], reg));
11414   DONE;
11415 })
11416
11417 ;; XOP FRCZ support
11418 (define_insn "xop_frcz<mode>2"
11419   [(set (match_operand:FMAMODE 0 "register_operand" "=x")
11420         (unspec:FMAMODE
11421          [(match_operand:FMAMODE 1 "nonimmediate_operand" "xm")]
11422          UNSPEC_FRCZ))]
11423   "TARGET_XOP"
11424   "vfrcz<ssemodesuffix>\t{%1, %0|%0, %1}"
11425   [(set_attr "type" "ssecvt1")
11426    (set_attr "mode" "<MODE>")])
11427
11428 ;; scalar insns
11429 (define_expand "xop_vmfrcz<mode>2"
11430   [(set (match_operand:VF_128 0 "register_operand")
11431         (vec_merge:VF_128
11432           (unspec:VF_128
11433            [(match_operand:VF_128 1 "nonimmediate_operand")]
11434            UNSPEC_FRCZ)
11435           (match_dup 3)
11436           (const_int 1)))]
11437   "TARGET_XOP"
11438 {
11439   operands[3] = CONST0_RTX (<MODE>mode);
11440 })
11441
11442 (define_insn "*xop_vmfrcz_<mode>"
11443   [(set (match_operand:VF_128 0 "register_operand" "=x")
11444         (vec_merge:VF_128
11445           (unspec:VF_128
11446            [(match_operand:VF_128 1 "nonimmediate_operand" "xm")]
11447            UNSPEC_FRCZ)
11448           (match_operand:VF_128 2 "const0_operand")
11449           (const_int 1)))]
11450   "TARGET_XOP"
11451   "vfrcz<ssescalarmodesuffix>\t{%1, %0|%0, %1}"
11452   [(set_attr "type" "ssecvt1")
11453    (set_attr "mode" "<MODE>")])
11454
11455 (define_insn "xop_maskcmp<mode>3"
11456   [(set (match_operand:VI_128 0 "register_operand" "=x")
11457         (match_operator:VI_128 1 "ix86_comparison_int_operator"
11458          [(match_operand:VI_128 2 "register_operand" "x")
11459           (match_operand:VI_128 3 "nonimmediate_operand" "xm")]))]
11460   "TARGET_XOP"
11461   "vpcom%Y1<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}"
11462   [(set_attr "type" "sse4arg")
11463    (set_attr "prefix_data16" "0")
11464    (set_attr "prefix_rep" "0")
11465    (set_attr "prefix_extra" "2")
11466    (set_attr "length_immediate" "1")
11467    (set_attr "mode" "TI")])
11468
11469 (define_insn "xop_maskcmp_uns<mode>3"
11470   [(set (match_operand:VI_128 0 "register_operand" "=x")
11471         (match_operator:VI_128 1 "ix86_comparison_uns_operator"
11472          [(match_operand:VI_128 2 "register_operand" "x")
11473           (match_operand:VI_128 3 "nonimmediate_operand" "xm")]))]
11474   "TARGET_XOP"
11475   "vpcom%Y1u<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}"
11476   [(set_attr "type" "ssecmp")
11477    (set_attr "prefix_data16" "0")
11478    (set_attr "prefix_rep" "0")
11479    (set_attr "prefix_extra" "2")
11480    (set_attr "length_immediate" "1")
11481    (set_attr "mode" "TI")])
11482
11483 ;; Version of pcom*u* that is called from the intrinsics that allows pcomequ*
11484 ;; and pcomneu* not to be converted to the signed ones in case somebody needs
11485 ;; the exact instruction generated for the intrinsic.
11486 (define_insn "xop_maskcmp_uns2<mode>3"
11487   [(set (match_operand:VI_128 0 "register_operand" "=x")
11488         (unspec:VI_128
11489          [(match_operator:VI_128 1 "ix86_comparison_uns_operator"
11490           [(match_operand:VI_128 2 "register_operand" "x")
11491            (match_operand:VI_128 3 "nonimmediate_operand" "xm")])]
11492          UNSPEC_XOP_UNSIGNED_CMP))]
11493   "TARGET_XOP"
11494   "vpcom%Y1u<ssemodesuffix>\t{%3, %2, %0|%0, %2, %3}"
11495   [(set_attr "type" "ssecmp")
11496    (set_attr "prefix_data16" "0")
11497    (set_attr "prefix_extra" "2")
11498    (set_attr "length_immediate" "1")
11499    (set_attr "mode" "TI")])
11500
11501 ;; Pcomtrue and pcomfalse support.  These are useless instructions, but are
11502 ;; being added here to be complete.
11503 (define_insn "xop_pcom_tf<mode>3"
11504   [(set (match_operand:VI_128 0 "register_operand" "=x")
11505         (unspec:VI_128
11506           [(match_operand:VI_128 1 "register_operand" "x")
11507            (match_operand:VI_128 2 "nonimmediate_operand" "xm")
11508            (match_operand:SI 3 "const_int_operand" "n")]
11509           UNSPEC_XOP_TRUEFALSE))]
11510   "TARGET_XOP"
11511 {
11512   return ((INTVAL (operands[3]) != 0)
11513           ? "vpcomtrue<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11514           : "vpcomfalse<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}");
11515 }
11516   [(set_attr "type" "ssecmp")
11517    (set_attr "prefix_data16" "0")
11518    (set_attr "prefix_extra" "2")
11519    (set_attr "length_immediate" "1")
11520    (set_attr "mode" "TI")])
11521
11522 (define_insn "xop_vpermil2<mode>3"
11523   [(set (match_operand:VF 0 "register_operand" "=x")
11524         (unspec:VF
11525           [(match_operand:VF 1 "register_operand" "x")
11526            (match_operand:VF 2 "nonimmediate_operand" "%x")
11527            (match_operand:<sseintvecmode> 3 "nonimmediate_operand" "xm")
11528            (match_operand:SI 4 "const_0_to_3_operand" "n")]
11529           UNSPEC_VPERMIL2))]
11530   "TARGET_XOP"
11531   "vpermil2<ssemodesuffix>\t{%4, %3, %2, %1, %0|%0, %1, %2, %3, %4}"
11532   [(set_attr "type" "sse4arg")
11533    (set_attr "length_immediate" "1")
11534    (set_attr "mode" "<MODE>")])
11535
11536 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
11537
11538 (define_insn "aesenc"
11539   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
11540         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0,x")
11541                        (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")]
11542                       UNSPEC_AESENC))]
11543   "TARGET_AES"
11544   "@
11545    aesenc\t{%2, %0|%0, %2}
11546    vaesenc\t{%2, %1, %0|%0, %1, %2}"
11547   [(set_attr "isa" "noavx,avx")
11548    (set_attr "type" "sselog1")
11549    (set_attr "prefix_extra" "1")
11550    (set_attr "prefix" "orig,vex")
11551    (set_attr "mode" "TI")])
11552
11553 (define_insn "aesenclast"
11554   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
11555         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0,x")
11556                        (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")]
11557                       UNSPEC_AESENCLAST))]
11558   "TARGET_AES"
11559   "@
11560    aesenclast\t{%2, %0|%0, %2}
11561    vaesenclast\t{%2, %1, %0|%0, %1, %2}"
11562   [(set_attr "isa" "noavx,avx")
11563    (set_attr "type" "sselog1")
11564    (set_attr "prefix_extra" "1")
11565    (set_attr "prefix" "orig,vex")
11566    (set_attr "mode" "TI")])
11567
11568 (define_insn "aesdec"
11569   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
11570         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0,x")
11571                        (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")]
11572                       UNSPEC_AESDEC))]
11573   "TARGET_AES"
11574   "@
11575    aesdec\t{%2, %0|%0, %2}
11576    vaesdec\t{%2, %1, %0|%0, %1, %2}"
11577   [(set_attr "isa" "noavx,avx")
11578    (set_attr "type" "sselog1")
11579    (set_attr "prefix_extra" "1")
11580    (set_attr "prefix" "orig,vex")
11581    (set_attr "mode" "TI")])
11582
11583 (define_insn "aesdeclast"
11584   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
11585         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0,x")
11586                        (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")]
11587                       UNSPEC_AESDECLAST))]
11588   "TARGET_AES"
11589   "@
11590    aesdeclast\t{%2, %0|%0, %2}
11591    vaesdeclast\t{%2, %1, %0|%0, %1, %2}"
11592   [(set_attr "isa" "noavx,avx")
11593    (set_attr "type" "sselog1")
11594    (set_attr "prefix_extra" "1")
11595    (set_attr "prefix" "orig,vex")
11596    (set_attr "mode" "TI")])
11597
11598 (define_insn "aesimc"
11599   [(set (match_operand:V2DI 0 "register_operand" "=x")
11600         (unspec:V2DI [(match_operand:V2DI 1 "nonimmediate_operand" "xm")]
11601                       UNSPEC_AESIMC))]
11602   "TARGET_AES"
11603   "%vaesimc\t{%1, %0|%0, %1}"
11604   [(set_attr "type" "sselog1")
11605    (set_attr "prefix_extra" "1")
11606    (set_attr "prefix" "maybe_vex")
11607    (set_attr "mode" "TI")])
11608
11609 (define_insn "aeskeygenassist"
11610   [(set (match_operand:V2DI 0 "register_operand" "=x")
11611         (unspec:V2DI [(match_operand:V2DI 1 "nonimmediate_operand" "xm")
11612                       (match_operand:SI 2 "const_0_to_255_operand" "n")]
11613                      UNSPEC_AESKEYGENASSIST))]
11614   "TARGET_AES"
11615   "%vaeskeygenassist\t{%2, %1, %0|%0, %1, %2}"
11616   [(set_attr "type" "sselog1")
11617    (set_attr "prefix_extra" "1")
11618    (set_attr "length_immediate" "1")
11619    (set_attr "prefix" "maybe_vex")
11620    (set_attr "mode" "TI")])
11621
11622 (define_insn "pclmulqdq"
11623   [(set (match_operand:V2DI 0 "register_operand" "=x,x")
11624         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "0,x")
11625                       (match_operand:V2DI 2 "nonimmediate_operand" "xm,xm")
11626                       (match_operand:SI 3 "const_0_to_255_operand" "n,n")]
11627                      UNSPEC_PCLMUL))]
11628   "TARGET_PCLMUL"
11629   "@
11630    pclmulqdq\t{%3, %2, %0|%0, %2, %3}
11631    vpclmulqdq\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11632   [(set_attr "isa" "noavx,avx")
11633    (set_attr "type" "sselog1")
11634    (set_attr "prefix_extra" "1")
11635    (set_attr "length_immediate" "1")
11636    (set_attr "prefix" "orig,vex")
11637    (set_attr "mode" "TI")])
11638
11639 (define_expand "avx_vzeroall"
11640   [(match_par_dup 0 [(const_int 0)])]
11641   "TARGET_AVX"
11642 {
11643   int nregs = TARGET_64BIT ? 16 : 8;
11644   int regno;
11645
11646   operands[0] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (nregs + 1));
11647
11648   XVECEXP (operands[0], 0, 0)
11649     = gen_rtx_UNSPEC_VOLATILE (VOIDmode, gen_rtvec (1, const0_rtx),
11650                                UNSPECV_VZEROALL);
11651
11652   for (regno = 0; regno < nregs; regno++)
11653     XVECEXP (operands[0], 0, regno + 1)
11654       = gen_rtx_SET (VOIDmode,
11655                      gen_rtx_REG (V8SImode, SSE_REGNO (regno)),
11656                      CONST0_RTX (V8SImode));
11657 })
11658
11659 (define_insn "*avx_vzeroall"
11660   [(match_parallel 0 "vzeroall_operation"
11661     [(unspec_volatile [(const_int 0)] UNSPECV_VZEROALL)])]
11662   "TARGET_AVX"
11663   "vzeroall"
11664   [(set_attr "type" "sse")
11665    (set_attr "modrm" "0")
11666    (set_attr "memory" "none")
11667    (set_attr "prefix" "vex")
11668    (set_attr "mode" "OI")])
11669
11670 ;; Clear the upper 128bits of AVX registers, equivalent to a NOP
11671 ;; if the upper 128bits are unused.
11672 (define_insn "avx_vzeroupper"
11673   [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
11674                     UNSPECV_VZEROUPPER)]
11675   "TARGET_AVX"
11676   "vzeroupper"
11677   [(set_attr "type" "sse")
11678    (set_attr "modrm" "0")
11679    (set_attr "memory" "none")
11680    (set_attr "prefix" "vex")
11681    (set_attr "mode" "OI")])
11682
11683 (define_mode_attr AVXTOSSEMODE
11684   [(V4DI "V2DI") (V2DI "V2DI")
11685    (V8SI "V4SI") (V4SI "V4SI")
11686    (V16HI "V8HI") (V8HI "V8HI")
11687    (V32QI "V16QI") (V16QI "V16QI")])
11688
11689 (define_insn "avx2_pbroadcast<mode>"
11690   [(set (match_operand:VI 0 "register_operand" "=x")
11691         (vec_duplicate:VI
11692           (vec_select:<ssescalarmode>
11693             (match_operand:<AVXTOSSEMODE> 1 "nonimmediate_operand" "xm")
11694             (parallel [(const_int 0)]))))]
11695   "TARGET_AVX2"
11696   "vpbroadcast<ssemodesuffix>\t{%1, %0|%0, %1}"
11697   [(set_attr "type" "ssemov")
11698    (set_attr "prefix_extra" "1")
11699    (set_attr "prefix" "vex")
11700    (set_attr "mode" "<sseinsnmode>")])
11701
11702 (define_insn "avx2_permvarv8si"
11703   [(set (match_operand:V8SI 0 "register_operand" "=x")
11704         (unspec:V8SI
11705           [(match_operand:V8SI 1 "register_operand" "x")
11706            (match_operand:V8SI 2 "nonimmediate_operand" "xm")]
11707           UNSPEC_VPERMSI))]
11708   "TARGET_AVX2"
11709   "vpermd\t{%2, %1, %0|%0, %1, %2}"
11710   [(set_attr "type" "sselog")
11711    (set_attr "prefix" "vex")
11712    (set_attr "mode" "OI")])
11713
11714 (define_insn "avx2_permv4df"
11715   [(set (match_operand:V4DF 0 "register_operand" "=x")
11716         (unspec:V4DF
11717           [(match_operand:V4DF 1 "register_operand" "xm")
11718            (match_operand:SI 2 "const_0_to_255_operand" "n")]
11719           UNSPEC_VPERMDF))]
11720   "TARGET_AVX2"
11721   "vpermpd\t{%2, %1, %0|%0, %1, %2}"
11722   [(set_attr "type" "sselog")
11723    (set_attr "prefix_extra" "1")
11724    (set_attr "prefix" "vex")
11725    (set_attr "mode" "OI")])
11726
11727 (define_insn "avx2_permvarv8sf"
11728   [(set (match_operand:V8SF 0 "register_operand" "=x")
11729         (unspec:V8SF
11730           [(match_operand:V8SF 1 "register_operand" "x")
11731            (match_operand:V8SF 2 "nonimmediate_operand" "xm")]
11732           UNSPEC_VPERMSF))]
11733   "TARGET_AVX2"
11734   "vpermps\t{%2, %1, %0|%0, %1, %2}"
11735   [(set_attr "type" "sselog")
11736    (set_attr "prefix" "vex")
11737    (set_attr "mode" "OI")])
11738
11739 (define_expand "avx2_permv4di"
11740   [(match_operand:V4DI 0 "register_operand" "")
11741    (match_operand:V4DI 1 "nonimmediate_operand" "")
11742    (match_operand:SI 2 "const_0_to_255_operand" "")]
11743   "TARGET_AVX2"
11744 {
11745   int mask = INTVAL (operands[2]);
11746   emit_insn (gen_avx2_permv4di_1 (operands[0], operands[1],
11747                                   GEN_INT ((mask >> 0) & 3),
11748                                   GEN_INT ((mask >> 2) & 3),
11749                                   GEN_INT ((mask >> 4) & 3),
11750                                   GEN_INT ((mask >> 6) & 3)));
11751   DONE;
11752 })
11753
11754 (define_insn "avx2_permv4di_1"
11755   [(set (match_operand:V4DI 0 "register_operand" "=x")
11756         (vec_select:V4DI
11757           (match_operand:V4DI 1 "nonimmediate_operand" "xm")
11758           (parallel [(match_operand 2 "const_0_to_3_operand" "")
11759                      (match_operand 3 "const_0_to_3_operand" "")
11760                      (match_operand 4 "const_0_to_3_operand" "")
11761                      (match_operand 5 "const_0_to_3_operand" "")])))]
11762   "TARGET_AVX2"
11763 {
11764   int mask = 0;
11765   mask |= INTVAL (operands[2]) << 0;
11766   mask |= INTVAL (operands[3]) << 2;
11767   mask |= INTVAL (operands[4]) << 4;
11768   mask |= INTVAL (operands[5]) << 6;
11769   operands[2] = GEN_INT (mask);
11770   return "vpermq\t{%2, %1, %0|%0, %1, %2}";
11771 }
11772   [(set_attr "type" "sselog")
11773    (set_attr "prefix" "vex")
11774    (set_attr "mode" "OI")])
11775
11776 (define_insn "avx2_permv2ti"
11777   [(set (match_operand:V4DI 0 "register_operand" "=x")
11778         (unspec:V4DI
11779           [(match_operand:V4DI 1 "register_operand" "x")
11780            (match_operand:V4DI 2 "nonimmediate_operand" "xm")
11781            (match_operand:SI 3 "const_0_to_255_operand" "n")]
11782           UNSPEC_VPERMTI))]
11783   "TARGET_AVX2"
11784   "vperm2i128\t{%3, %2, %1, %0|%0, %1, %2, %3}"
11785   [(set_attr "type" "sselog")
11786    (set_attr "prefix" "vex")
11787    (set_attr "mode" "OI")])
11788
11789 (define_insn "avx2_vec_dupv4df"
11790   [(set (match_operand:V4DF 0 "register_operand" "=x")
11791         (vec_duplicate:V4DF
11792           (vec_select:DF
11793             (match_operand:V2DF 1 "register_operand" "x")
11794             (parallel [(const_int 0)]))))]
11795   "TARGET_AVX2"
11796   "vbroadcastsd\t{%1, %0|%0, %1}"
11797   [(set_attr "type" "sselog1")
11798    (set_attr "prefix" "vex")
11799    (set_attr "mode" "V4DF")])
11800
11801 ;; Modes handled by AVX vec_dup patterns.
11802 (define_mode_iterator AVX_VEC_DUP_MODE
11803   [V8SI V8SF V4DI V4DF])
11804
11805 (define_insn "vec_dup<mode>"
11806   [(set (match_operand:AVX_VEC_DUP_MODE 0 "register_operand" "=x,x")
11807         (vec_duplicate:AVX_VEC_DUP_MODE
11808           (match_operand:<ssescalarmode> 1 "nonimmediate_operand" "m,?x")))]
11809   "TARGET_AVX"
11810   "@
11811    vbroadcast<ssescalarmodesuffix>\t{%1, %0|%0, %1}
11812    #"
11813   [(set_attr "type" "ssemov")
11814    (set_attr "prefix_extra" "1")
11815    (set_attr "prefix" "vex")
11816    (set_attr "mode" "V8SF")])
11817
11818 (define_insn "avx2_vbroadcasti128_<mode>"
11819   [(set (match_operand:VI_256 0 "register_operand" "=x")
11820         (vec_concat:VI_256
11821           (match_operand:<ssehalfvecmode> 1 "memory_operand" "m")
11822           (match_dup 1)))]
11823   "TARGET_AVX2"
11824   "vbroadcasti128\t{%1, %0|%0, %1}"
11825   [(set_attr "type" "ssemov")
11826    (set_attr "prefix_extra" "1")
11827    (set_attr "prefix" "vex")
11828    (set_attr "mode" "OI")])
11829
11830 (define_split
11831   [(set (match_operand:AVX_VEC_DUP_MODE 0 "register_operand" "")
11832         (vec_duplicate:AVX_VEC_DUP_MODE
11833           (match_operand:<ssescalarmode> 1 "register_operand" "")))]
11834   "TARGET_AVX && reload_completed"
11835   [(set (match_dup 2)
11836         (vec_duplicate:<ssehalfvecmode> (match_dup 1)))
11837    (set (match_dup 0)
11838         (vec_concat:AVX_VEC_DUP_MODE (match_dup 2) (match_dup 2)))]
11839   "operands[2] = gen_rtx_REG (<ssehalfvecmode>mode, REGNO (operands[0]));")
11840
11841 (define_insn "avx_vbroadcastf128_<mode>"
11842   [(set (match_operand:V_256 0 "register_operand" "=x,x,x")
11843         (vec_concat:V_256
11844           (match_operand:<ssehalfvecmode> 1 "nonimmediate_operand" "m,0,?x")
11845           (match_dup 1)))]
11846   "TARGET_AVX"
11847   "@
11848    vbroadcast<i128>\t{%1, %0|%0, %1}
11849    vinsert<i128>\t{$1, %1, %0, %0|%0, %0, %1, 1}
11850    vperm2<i128>\t{$0, %t1, %t1, %0|%0, %t1, %t1, 0}"
11851   [(set_attr "type" "ssemov,sselog1,sselog1")
11852    (set_attr "prefix_extra" "1")
11853    (set_attr "length_immediate" "0,1,1")
11854    (set_attr "prefix" "vex")
11855    (set_attr "mode" "<sseinsnmode>")])
11856
11857 ;; Recognize broadcast as a vec_select as produced by builtin_vec_perm.
11858 ;; If it so happens that the input is in memory, use vbroadcast.
11859 ;; Otherwise use vpermilp (and in the case of 256-bit modes, vperm2f128).
11860 (define_insn "*avx_vperm_broadcast_v4sf"
11861   [(set (match_operand:V4SF 0 "register_operand" "=x,x,x")
11862         (vec_select:V4SF
11863           (match_operand:V4SF 1 "nonimmediate_operand" "m,o,x")
11864           (match_parallel 2 "avx_vbroadcast_operand"
11865             [(match_operand 3 "const_int_operand" "C,n,n")])))]
11866   "TARGET_AVX"
11867 {
11868   int elt = INTVAL (operands[3]);
11869   switch (which_alternative)
11870     {
11871     case 0:
11872     case 1:
11873       operands[1] = adjust_address_nv (operands[1], SFmode, elt * 4);
11874       return "vbroadcastss\t{%1, %0|%0, %1}";
11875     case 2:
11876       operands[2] = GEN_INT (elt * 0x55);
11877       return "vpermilps\t{%2, %1, %0|%0, %1, %2}";
11878     default:
11879       gcc_unreachable ();
11880     }
11881 }
11882   [(set_attr "type" "ssemov,ssemov,sselog1")
11883    (set_attr "prefix_extra" "1")
11884    (set_attr "length_immediate" "0,0,1")
11885    (set_attr "prefix" "vex")
11886    (set_attr "mode" "SF,SF,V4SF")])
11887
11888 (define_insn_and_split "*avx_vperm_broadcast_<mode>"
11889   [(set (match_operand:VF_256 0 "register_operand" "=x,x,x")
11890         (vec_select:VF_256
11891           (match_operand:VF_256 1 "nonimmediate_operand" "m,o,?x")
11892           (match_parallel 2 "avx_vbroadcast_operand"
11893             [(match_operand 3 "const_int_operand" "C,n,n")])))]
11894   "TARGET_AVX"
11895   "#"
11896   "&& reload_completed"
11897   [(set (match_dup 0) (vec_duplicate:VF_256 (match_dup 1)))]
11898 {
11899   rtx op0 = operands[0], op1 = operands[1];
11900   int elt = INTVAL (operands[3]);
11901
11902   if (REG_P (op1))
11903     {
11904       int mask;
11905
11906       /* Shuffle element we care about into all elements of the 128-bit lane.
11907          The other lane gets shuffled too, but we don't care.  */
11908       if (<MODE>mode == V4DFmode)
11909         mask = (elt & 1 ? 15 : 0);
11910       else
11911         mask = (elt & 3) * 0x55;
11912       emit_insn (gen_avx_vpermil<mode> (op0, op1, GEN_INT (mask)));
11913
11914       /* Shuffle the lane we care about into both lanes of the dest.  */
11915       mask = (elt / (<ssescalarnum> / 2)) * 0x11;
11916       emit_insn (gen_avx_vperm2f128<mode>3 (op0, op0, op0, GEN_INT (mask)));
11917       DONE;
11918     }
11919
11920   operands[1] = adjust_address_nv (op1, <ssescalarmode>mode,
11921                                    elt * GET_MODE_SIZE (<ssescalarmode>mode));
11922 })
11923
11924 (define_expand "avx_vpermil<mode>"
11925   [(set (match_operand:VF2 0 "register_operand" "")
11926         (vec_select:VF2
11927           (match_operand:VF2 1 "nonimmediate_operand" "")
11928           (match_operand:SI 2 "const_0_to_255_operand" "")))]
11929   "TARGET_AVX"
11930 {
11931   int mask = INTVAL (operands[2]);
11932   rtx perm[<ssescalarnum>];
11933
11934   perm[0] = GEN_INT (mask & 1);
11935   perm[1] = GEN_INT ((mask >> 1) & 1);
11936   if (<MODE>mode == V4DFmode)
11937     {
11938       perm[2] = GEN_INT (((mask >> 2) & 1) + 2);
11939       perm[3] = GEN_INT (((mask >> 3) & 1) + 2);
11940     }
11941
11942   operands[2]
11943     = gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (<ssescalarnum>, perm));
11944 })
11945
11946 (define_expand "avx_vpermil<mode>"
11947   [(set (match_operand:VF1 0 "register_operand" "")
11948         (vec_select:VF1
11949           (match_operand:VF1 1 "nonimmediate_operand" "")
11950           (match_operand:SI 2 "const_0_to_255_operand" "")))]
11951   "TARGET_AVX"
11952 {
11953   int mask = INTVAL (operands[2]);
11954   rtx perm[<ssescalarnum>];
11955
11956   perm[0] = GEN_INT (mask & 3);
11957   perm[1] = GEN_INT ((mask >> 2) & 3);
11958   perm[2] = GEN_INT ((mask >> 4) & 3);
11959   perm[3] = GEN_INT ((mask >> 6) & 3);
11960   if (<MODE>mode == V8SFmode)
11961     {
11962       perm[4] = GEN_INT ((mask & 3) + 4);
11963       perm[5] = GEN_INT (((mask >> 2) & 3) + 4);
11964       perm[6] = GEN_INT (((mask >> 4) & 3) + 4);
11965       perm[7] = GEN_INT (((mask >> 6) & 3) + 4);
11966     }
11967
11968   operands[2]
11969     = gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (<ssescalarnum>, perm));
11970 })
11971
11972 (define_insn "*avx_vpermilp<mode>"
11973   [(set (match_operand:VF 0 "register_operand" "=x")
11974         (vec_select:VF
11975           (match_operand:VF 1 "nonimmediate_operand" "xm")
11976           (match_parallel 2 ""
11977             [(match_operand 3 "const_int_operand" "")])))]
11978   "TARGET_AVX
11979    && avx_vpermilp_parallel (operands[2], <MODE>mode)"
11980 {
11981   int mask = avx_vpermilp_parallel (operands[2], <MODE>mode) - 1;
11982   operands[2] = GEN_INT (mask);
11983   return "vpermil<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}";
11984 }
11985   [(set_attr "type" "sselog")
11986    (set_attr "prefix_extra" "1")
11987    (set_attr "length_immediate" "1")
11988    (set_attr "prefix" "vex")
11989    (set_attr "mode" "<MODE>")])
11990
11991 (define_insn "avx_vpermilvar<mode>3"
11992   [(set (match_operand:VF 0 "register_operand" "=x")
11993         (unspec:VF
11994           [(match_operand:VF 1 "register_operand" "x")
11995            (match_operand:<sseintvecmode> 2 "nonimmediate_operand" "xm")]
11996           UNSPEC_VPERMIL))]
11997   "TARGET_AVX"
11998   "vpermil<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
11999   [(set_attr "type" "sselog")
12000    (set_attr "prefix_extra" "1")
12001    (set_attr "prefix" "vex")
12002    (set_attr "mode" "<MODE>")])
12003
12004 (define_expand "avx_vperm2f128<mode>3"
12005   [(set (match_operand:AVX256MODE2P 0 "register_operand" "")
12006         (unspec:AVX256MODE2P
12007           [(match_operand:AVX256MODE2P 1 "register_operand" "")
12008            (match_operand:AVX256MODE2P 2 "nonimmediate_operand" "")
12009            (match_operand:SI 3 "const_0_to_255_operand" "")]
12010           UNSPEC_VPERMIL2F128))]
12011   "TARGET_AVX"
12012 {
12013   int mask = INTVAL (operands[3]);
12014   if ((mask & 0x88) == 0)
12015     {
12016       rtx perm[<ssescalarnum>], t1, t2;
12017       int i, base, nelt = <ssescalarnum>, nelt2 = nelt / 2;
12018
12019       base = (mask & 3) * nelt2;
12020       for (i = 0; i < nelt2; ++i)
12021         perm[i] = GEN_INT (base + i);
12022
12023       base = ((mask >> 4) & 3) * nelt2;
12024       for (i = 0; i < nelt2; ++i)
12025         perm[i + nelt2] = GEN_INT (base + i);
12026
12027       t2 = gen_rtx_VEC_CONCAT (<ssedoublevecmode>mode,
12028                                operands[1], operands[2]);
12029       t1 = gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (nelt, perm));
12030       t2 = gen_rtx_VEC_SELECT (<MODE>mode, t2, t1);
12031       t2 = gen_rtx_SET (VOIDmode, operands[0], t2);
12032       emit_insn (t2);
12033       DONE;
12034     }
12035 })
12036
12037 ;; Note that bits 7 and 3 of the imm8 allow lanes to be zeroed, which
12038 ;; means that in order to represent this properly in rtl we'd have to
12039 ;; nest *another* vec_concat with a zero operand and do the select from
12040 ;; a 4x wide vector.  That doesn't seem very nice.
12041 (define_insn "*avx_vperm2f128<mode>_full"
12042   [(set (match_operand:AVX256MODE2P 0 "register_operand" "=x")
12043         (unspec:AVX256MODE2P
12044           [(match_operand:AVX256MODE2P 1 "register_operand" "x")
12045            (match_operand:AVX256MODE2P 2 "nonimmediate_operand" "xm")
12046            (match_operand:SI 3 "const_0_to_255_operand" "n")]
12047           UNSPEC_VPERMIL2F128))]
12048   "TARGET_AVX"
12049   "vperm2<i128>\t{%3, %2, %1, %0|%0, %1, %2, %3}"
12050   [(set_attr "type" "sselog")
12051    (set_attr "prefix_extra" "1")
12052    (set_attr "length_immediate" "1")
12053    (set_attr "prefix" "vex")
12054    (set_attr "mode" "<sseinsnmode>")])
12055
12056 (define_insn "*avx_vperm2f128<mode>_nozero"
12057   [(set (match_operand:AVX256MODE2P 0 "register_operand" "=x")
12058         (vec_select:AVX256MODE2P
12059           (vec_concat:<ssedoublevecmode>
12060             (match_operand:AVX256MODE2P 1 "register_operand" "x")
12061             (match_operand:AVX256MODE2P 2 "nonimmediate_operand" "xm"))
12062           (match_parallel 3 ""
12063             [(match_operand 4 "const_int_operand" "")])))]
12064   "TARGET_AVX
12065    && avx_vperm2f128_parallel (operands[3], <MODE>mode)"
12066 {
12067   int mask = avx_vperm2f128_parallel (operands[3], <MODE>mode) - 1;
12068   operands[3] = GEN_INT (mask);
12069   return "vperm2<i128>\t{%3, %2, %1, %0|%0, %1, %2, %3}";
12070 }
12071   [(set_attr "type" "sselog")
12072    (set_attr "prefix_extra" "1")
12073    (set_attr "length_immediate" "1")
12074    (set_attr "prefix" "vex")
12075    (set_attr "mode" "<sseinsnmode>")])
12076
12077 (define_expand "avx_vinsertf128<mode>"
12078   [(match_operand:V_256 0 "register_operand" "")
12079    (match_operand:V_256 1 "register_operand" "")
12080    (match_operand:<ssehalfvecmode> 2 "nonimmediate_operand" "")
12081    (match_operand:SI 3 "const_0_to_1_operand" "")]
12082   "TARGET_AVX"
12083 {
12084   rtx (*insn)(rtx, rtx, rtx);
12085
12086   switch (INTVAL (operands[3]))
12087     {
12088     case 0:
12089       insn = gen_vec_set_lo_<mode>;
12090       break;
12091     case 1:
12092       insn = gen_vec_set_hi_<mode>;
12093       break;
12094     default:
12095       gcc_unreachable ();
12096     }
12097
12098   emit_insn (insn (operands[0], operands[1], operands[2]));
12099   DONE;
12100 })
12101
12102 (define_insn "avx2_vec_set_lo_v4di"
12103   [(set (match_operand:V4DI 0 "register_operand" "=x")
12104         (vec_concat:V4DI
12105           (match_operand:V2DI 2 "nonimmediate_operand" "xm")
12106           (vec_select:V2DI
12107             (match_operand:V4DI 1 "register_operand" "x")
12108             (parallel [(const_int 2) (const_int 3)]))))]
12109   "TARGET_AVX2"
12110   "vinserti128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
12111   [(set_attr "type" "sselog")
12112    (set_attr "prefix_extra" "1")
12113    (set_attr "length_immediate" "1")
12114    (set_attr "prefix" "vex")
12115    (set_attr "mode" "OI")])
12116
12117 (define_insn "avx2_vec_set_hi_v4di"
12118   [(set (match_operand:V4DI 0 "register_operand" "=x")
12119         (vec_concat:V4DI
12120           (vec_select:V2DI
12121             (match_operand:V4DI 1 "register_operand" "x")
12122             (parallel [(const_int 0) (const_int 1)]))
12123           (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
12124   "TARGET_AVX2"
12125   "vinserti128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
12126   [(set_attr "type" "sselog")
12127    (set_attr "prefix_extra" "1")
12128    (set_attr "length_immediate" "1")
12129    (set_attr "prefix" "vex")
12130    (set_attr "mode" "OI")])
12131
12132 (define_insn "vec_set_lo_<mode>"
12133   [(set (match_operand:VI8F_256 0 "register_operand" "=x")
12134         (vec_concat:VI8F_256
12135           (match_operand:<ssehalfvecmode> 2 "nonimmediate_operand" "xm")
12136           (vec_select:<ssehalfvecmode>
12137             (match_operand:VI8F_256 1 "register_operand" "x")
12138             (parallel [(const_int 2) (const_int 3)]))))]
12139   "TARGET_AVX"
12140   "vinsert<i128>\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
12141   [(set_attr "type" "sselog")
12142    (set_attr "prefix_extra" "1")
12143    (set_attr "length_immediate" "1")
12144    (set_attr "prefix" "vex")
12145    (set_attr "mode" "<sseinsnmode>")])
12146
12147 (define_insn "vec_set_hi_<mode>"
12148   [(set (match_operand:VI8F_256 0 "register_operand" "=x")
12149         (vec_concat:VI8F_256
12150           (vec_select:<ssehalfvecmode>
12151             (match_operand:VI8F_256 1 "register_operand" "x")
12152             (parallel [(const_int 0) (const_int 1)]))
12153           (match_operand:<ssehalfvecmode> 2 "nonimmediate_operand" "xm")))]
12154   "TARGET_AVX"
12155   "vinsert<i128>\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
12156   [(set_attr "type" "sselog")
12157    (set_attr "prefix_extra" "1")
12158    (set_attr "length_immediate" "1")
12159    (set_attr "prefix" "vex")
12160    (set_attr "mode" "<sseinsnmode>")])
12161
12162 (define_insn "vec_set_lo_<mode>"
12163   [(set (match_operand:VI4F_256 0 "register_operand" "=x")
12164         (vec_concat:VI4F_256
12165           (match_operand:<ssehalfvecmode> 2 "nonimmediate_operand" "xm")
12166           (vec_select:<ssehalfvecmode>
12167             (match_operand:VI4F_256 1 "register_operand" "x")
12168             (parallel [(const_int 4) (const_int 5)
12169                        (const_int 6) (const_int 7)]))))]
12170   "TARGET_AVX"
12171   "vinsert<i128>\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
12172   [(set_attr "type" "sselog")
12173    (set_attr "prefix_extra" "1")
12174    (set_attr "length_immediate" "1")
12175    (set_attr "prefix" "vex")
12176    (set_attr "mode" "<sseinsnmode>")])
12177
12178 (define_insn "vec_set_hi_<mode>"
12179   [(set (match_operand:VI4F_256 0 "register_operand" "=x")
12180         (vec_concat:VI4F_256
12181           (vec_select:<ssehalfvecmode>
12182             (match_operand:VI4F_256 1 "register_operand" "x")
12183             (parallel [(const_int 0) (const_int 1)
12184                        (const_int 2) (const_int 3)]))
12185           (match_operand:<ssehalfvecmode> 2 "nonimmediate_operand" "xm")))]
12186   "TARGET_AVX"
12187   "vinsert<i128>\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
12188   [(set_attr "type" "sselog")
12189    (set_attr "prefix_extra" "1")
12190    (set_attr "length_immediate" "1")
12191    (set_attr "prefix" "vex")
12192    (set_attr "mode" "<sseinsnmode>")])
12193
12194 (define_insn "vec_set_lo_v16hi"
12195   [(set (match_operand:V16HI 0 "register_operand" "=x")
12196         (vec_concat:V16HI
12197           (match_operand:V8HI 2 "nonimmediate_operand" "xm")
12198           (vec_select:V8HI
12199             (match_operand:V16HI 1 "register_operand" "x")
12200             (parallel [(const_int 8) (const_int 9)
12201                        (const_int 10) (const_int 11)
12202                        (const_int 12) (const_int 13)
12203                        (const_int 14) (const_int 15)]))))]
12204   "TARGET_AVX"
12205   "vinsert%~128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
12206   [(set_attr "type" "sselog")
12207    (set_attr "prefix_extra" "1")
12208    (set_attr "length_immediate" "1")
12209    (set_attr "prefix" "vex")
12210    (set_attr "mode" "OI")])
12211
12212 (define_insn "vec_set_hi_v16hi"
12213   [(set (match_operand:V16HI 0 "register_operand" "=x")
12214         (vec_concat:V16HI
12215           (vec_select:V8HI
12216             (match_operand:V16HI 1 "register_operand" "x")
12217             (parallel [(const_int 0) (const_int 1)
12218                        (const_int 2) (const_int 3)
12219                        (const_int 4) (const_int 5)
12220                        (const_int 6) (const_int 7)]))
12221           (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
12222   "TARGET_AVX"
12223   "vinsert%~128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
12224   [(set_attr "type" "sselog")
12225    (set_attr "prefix_extra" "1")
12226    (set_attr "length_immediate" "1")
12227    (set_attr "prefix" "vex")
12228    (set_attr "mode" "OI")])
12229
12230 (define_insn "vec_set_lo_v32qi"
12231   [(set (match_operand:V32QI 0 "register_operand" "=x")
12232         (vec_concat:V32QI
12233           (match_operand:V16QI 2 "nonimmediate_operand" "xm")
12234           (vec_select:V16QI
12235             (match_operand:V32QI 1 "register_operand" "x")
12236             (parallel [(const_int 16) (const_int 17)
12237                        (const_int 18) (const_int 19)
12238                        (const_int 20) (const_int 21)
12239                        (const_int 22) (const_int 23)
12240                        (const_int 24) (const_int 25)
12241                        (const_int 26) (const_int 27)
12242                        (const_int 28) (const_int 29)
12243                        (const_int 30) (const_int 31)]))))]
12244   "TARGET_AVX"
12245   "vinsert%~128\t{$0x0, %2, %1, %0|%0, %1, %2, 0x0}"
12246   [(set_attr "type" "sselog")
12247    (set_attr "prefix_extra" "1")
12248    (set_attr "length_immediate" "1")
12249    (set_attr "prefix" "vex")
12250    (set_attr "mode" "OI")])
12251
12252 (define_insn "vec_set_hi_v32qi"
12253   [(set (match_operand:V32QI 0 "register_operand" "=x")
12254         (vec_concat:V32QI
12255           (vec_select:V16QI
12256             (match_operand:V32QI 1 "register_operand" "x")
12257             (parallel [(const_int 0) (const_int 1)
12258                        (const_int 2) (const_int 3)
12259                        (const_int 4) (const_int 5)
12260                        (const_int 6) (const_int 7)
12261                        (const_int 8) (const_int 9)
12262                        (const_int 10) (const_int 11)
12263                        (const_int 12) (const_int 13)
12264                        (const_int 14) (const_int 15)]))
12265           (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
12266   "TARGET_AVX"
12267   "vinsert%~128\t{$0x1, %2, %1, %0|%0, %1, %2, 0x1}"
12268   [(set_attr "type" "sselog")
12269    (set_attr "prefix_extra" "1")
12270    (set_attr "length_immediate" "1")
12271    (set_attr "prefix" "vex")
12272    (set_attr "mode" "OI")])
12273
12274 (define_insn "<avx_avx2>_maskload<ssemodesuffix><avxsizesuffix>"
12275   [(set (match_operand:V48_AVX2 0 "register_operand" "=x")
12276         (unspec:V48_AVX2
12277           [(match_operand:<sseintvecmode> 2 "register_operand" "x")
12278            (match_operand:V48_AVX2 1 "memory_operand" "m")]
12279           UNSPEC_MASKMOV))]
12280   "TARGET_AVX"
12281   "v<sseintprefix>maskmov<ssemodesuffix>\t{%1, %2, %0|%0, %2, %1}"
12282   [(set_attr "type" "sselog1")
12283    (set_attr "prefix_extra" "1")
12284    (set_attr "prefix" "vex")
12285    (set_attr "mode" "<sseinsnmode>")])
12286
12287 (define_insn "<avx_avx2>_maskstore<ssemodesuffix><avxsizesuffix>"
12288   [(set (match_operand:V48_AVX2 0 "memory_operand" "=m")
12289         (unspec:V48_AVX2
12290           [(match_operand:<sseintvecmode> 1 "register_operand" "x")
12291            (match_operand:V48_AVX2 2 "register_operand" "x")
12292            (match_dup 0)]
12293           UNSPEC_MASKMOV))]
12294   "TARGET_AVX"
12295   "v<sseintprefix>maskmov<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
12296   [(set_attr "type" "sselog1")
12297    (set_attr "prefix_extra" "1")
12298    (set_attr "prefix" "vex")
12299    (set_attr "mode" "<sseinsnmode>")])
12300
12301 (define_insn_and_split "avx_<castmode><avxsizesuffix>_<castmode>"
12302   [(set (match_operand:AVX256MODE2P 0 "nonimmediate_operand" "=x,m")
12303         (unspec:AVX256MODE2P
12304           [(match_operand:<ssehalfvecmode> 1 "nonimmediate_operand" "xm,x")]
12305           UNSPEC_CAST))]
12306   "TARGET_AVX"
12307   "#"
12308   "&& reload_completed"
12309   [(const_int 0)]
12310 {
12311   rtx op0 = operands[0];
12312   rtx op1 = operands[1];
12313   if (REG_P (op0))
12314     op0 = gen_rtx_REG (<ssehalfvecmode>mode, REGNO (op0));
12315   else
12316     op1 = gen_rtx_REG (<MODE>mode, REGNO (op1));
12317   emit_move_insn (op0, op1);
12318   DONE;
12319 })
12320
12321 (define_expand "vec_init<mode>"
12322   [(match_operand:V_256 0 "register_operand" "")
12323    (match_operand 1 "" "")]
12324   "TARGET_AVX"
12325 {
12326   ix86_expand_vector_init (false, operands[0], operands[1]);
12327   DONE;
12328 })
12329
12330 (define_expand "avx2_extracti128"
12331   [(match_operand:V2DI 0 "nonimmediate_operand" "")
12332    (match_operand:V4DI 1 "register_operand" "")
12333    (match_operand:SI 2 "const_0_to_1_operand" "")]
12334   "TARGET_AVX2"
12335 {
12336   rtx (*insn)(rtx, rtx);
12337
12338   switch (INTVAL (operands[2]))
12339     {
12340     case 0:
12341       insn = gen_vec_extract_lo_v4di;
12342       break;
12343     case 1:
12344       insn = gen_vec_extract_hi_v4di;
12345       break;
12346     default:
12347       gcc_unreachable ();
12348     }
12349
12350   emit_insn (insn (operands[0], operands[1]));
12351   DONE;
12352 })
12353
12354 (define_expand "avx2_inserti128"
12355   [(match_operand:V4DI 0 "register_operand" "")
12356    (match_operand:V4DI 1 "register_operand" "")
12357    (match_operand:V2DI 2 "nonimmediate_operand" "")
12358    (match_operand:SI 3 "const_0_to_1_operand" "")]
12359   "TARGET_AVX2"
12360 {
12361   rtx (*insn)(rtx, rtx, rtx);
12362
12363   switch (INTVAL (operands[3]))
12364     {
12365     case 0:
12366       insn = gen_avx2_vec_set_lo_v4di;
12367       break;
12368     case 1:
12369       insn = gen_avx2_vec_set_hi_v4di;
12370       break;
12371     default:
12372       gcc_unreachable ();
12373     }
12374
12375   emit_insn (insn (operands[0], operands[1], operands[2]));
12376   DONE;
12377 })
12378
12379 (define_insn "avx2_ashrv<mode>"
12380   [(set (match_operand:VI4_AVX2 0 "register_operand" "=x")
12381         (ashiftrt:VI4_AVX2
12382           (match_operand:VI4_AVX2 1 "register_operand" "x")
12383           (match_operand:VI4_AVX2 2 "nonimmediate_operand" "xm")))]
12384   "TARGET_AVX2"
12385   "vpsravd\t{%2, %1, %0|%0, %1, %2}"
12386   [(set_attr "type" "sseishft")
12387    (set_attr "prefix" "vex")
12388    (set_attr "mode" "<sseinsnmode>")])
12389
12390 (define_insn "avx2_<shift_insn>v<mode>"
12391   [(set (match_operand:VI48_AVX2 0 "register_operand" "=x")
12392         (any_lshift:VI48_AVX2
12393           (match_operand:VI48_AVX2 1 "register_operand" "x")
12394           (match_operand:VI48_AVX2 2 "nonimmediate_operand" "xm")))]
12395   "TARGET_AVX2"
12396   "vp<vshift>v<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
12397   [(set_attr "type" "sseishft")
12398    (set_attr "prefix" "vex")
12399    (set_attr "mode" "<sseinsnmode>")])
12400
12401 (define_insn "avx_vec_concat<mode>"
12402   [(set (match_operand:V_256 0 "register_operand" "=x,x")
12403         (vec_concat:V_256
12404           (match_operand:<ssehalfvecmode> 1 "register_operand" "x,x")
12405           (match_operand:<ssehalfvecmode> 2 "vector_move_operand" "xm,C")))]
12406   "TARGET_AVX"
12407 {
12408   switch (which_alternative)
12409     {
12410     case 0:
12411       return "vinsert<i128>\t{$0x1, %2, %t1, %0|%0, %t1, %2, 0x1}";
12412     case 1:
12413       switch (get_attr_mode (insn))
12414         {
12415         case MODE_V8SF:
12416           return "vmovaps\t{%1, %x0|%x0, %1}";
12417         case MODE_V4DF:
12418           return "vmovapd\t{%1, %x0|%x0, %1}";
12419         default:
12420           return "vmovdqa\t{%1, %x0|%x0, %1}";
12421         }
12422     default:
12423       gcc_unreachable ();
12424     }
12425 }
12426   [(set_attr "type" "sselog,ssemov")
12427    (set_attr "prefix_extra" "1,*")
12428    (set_attr "length_immediate" "1,*")
12429    (set_attr "prefix" "vex")
12430    (set_attr "mode" "<sseinsnmode>")])
12431
12432 (define_insn "vcvtph2ps"
12433   [(set (match_operand:V4SF 0 "register_operand" "=x")
12434         (vec_select:V4SF
12435           (unspec:V8SF [(match_operand:V8HI 1 "register_operand" "x")]
12436                        UNSPEC_VCVTPH2PS)
12437           (parallel [(const_int 0) (const_int 1)
12438                      (const_int 1) (const_int 2)])))]
12439   "TARGET_F16C"
12440   "vcvtph2ps\t{%1, %0|%0, %1}"
12441   [(set_attr "type" "ssecvt")
12442    (set_attr "prefix" "vex")
12443    (set_attr "mode" "V4SF")])
12444
12445 (define_insn "*vcvtph2ps_load"
12446   [(set (match_operand:V4SF 0 "register_operand" "=x")
12447         (unspec:V4SF [(match_operand:V4HI 1 "memory_operand" "m")]
12448                      UNSPEC_VCVTPH2PS))]
12449   "TARGET_F16C"
12450   "vcvtph2ps\t{%1, %0|%0, %1}"
12451   [(set_attr "type" "ssecvt")
12452    (set_attr "prefix" "vex")
12453    (set_attr "mode" "V8SF")])
12454
12455 (define_insn "vcvtph2ps256"
12456   [(set (match_operand:V8SF 0 "register_operand" "=x")
12457         (unspec:V8SF [(match_operand:V8HI 1 "nonimmediate_operand" "xm")]
12458                      UNSPEC_VCVTPH2PS))]
12459   "TARGET_F16C"
12460   "vcvtph2ps\t{%1, %0|%0, %1}"
12461   [(set_attr "type" "ssecvt")
12462    (set_attr "prefix" "vex")
12463    (set_attr "mode" "V8SF")])
12464
12465 (define_expand "vcvtps2ph"
12466   [(set (match_operand:V8HI 0 "register_operand" "")
12467         (vec_concat:V8HI
12468           (unspec:V4HI [(match_operand:V4SF 1 "register_operand" "")
12469                         (match_operand:SI 2 "const_0_to_255_operand" "")]
12470                        UNSPEC_VCVTPS2PH)
12471           (match_dup 3)))]
12472   "TARGET_F16C"
12473   "operands[3] = CONST0_RTX (V4HImode);")
12474
12475 (define_insn "*vcvtps2ph"
12476   [(set (match_operand:V8HI 0 "register_operand" "=x")
12477         (vec_concat:V8HI
12478           (unspec:V4HI [(match_operand:V4SF 1 "register_operand" "x")
12479                         (match_operand:SI 2 "const_0_to_255_operand" "N")]
12480                        UNSPEC_VCVTPS2PH)
12481           (match_operand:V4HI 3 "const0_operand" "")))]
12482   "TARGET_F16C"
12483   "vcvtps2ph\t{%2, %1, %0|%0, %1, %2}"
12484   [(set_attr "type" "ssecvt")
12485    (set_attr "prefix" "vex")
12486    (set_attr "mode" "V4SF")])
12487
12488 (define_insn "*vcvtps2ph_store"
12489   [(set (match_operand:V4HI 0 "memory_operand" "=m")
12490         (unspec:V4HI [(match_operand:V4SF 1 "register_operand" "x")
12491                       (match_operand:SI 2 "const_0_to_255_operand" "N")]
12492                      UNSPEC_VCVTPS2PH))]
12493   "TARGET_F16C"
12494   "vcvtps2ph\t{%2, %1, %0|%0, %1, %2}"
12495   [(set_attr "type" "ssecvt")
12496    (set_attr "prefix" "vex")
12497    (set_attr "mode" "V4SF")])
12498
12499 (define_insn "vcvtps2ph256"
12500   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=xm")
12501         (unspec:V8HI [(match_operand:V8SF 1 "register_operand" "x")
12502                       (match_operand:SI 2 "const_0_to_255_operand" "N")]
12503                      UNSPEC_VCVTPS2PH))]
12504   "TARGET_F16C"
12505   "vcvtps2ph\t{%2, %1, %0|%0, %1, %2}"
12506   [(set_attr "type" "ssecvt")
12507    (set_attr "prefix" "vex")
12508    (set_attr "mode" "V8SF")])
12509
12510 ;; For gather* insn patterns
12511 (define_mode_iterator VEC_GATHER_MODE
12512                       [V2DI V2DF V4DI V4DF V4SI V4SF V8SI V8SF])
12513 (define_mode_attr VEC_GATHER_IDXSI
12514                       [(V2DI "V4SI") (V2DF "V4SI")
12515                        (V4DI "V4SI") (V4DF "V4SI")
12516                        (V4SI "V4SI") (V4SF "V4SI")
12517                        (V8SI "V8SI") (V8SF "V8SI")])
12518 (define_mode_attr VEC_GATHER_IDXDI
12519                       [(V2DI "V2DI") (V2DF "V2DI")
12520                        (V4DI "V4DI") (V4DF "V4DI")
12521                        (V4SI "V2DI") (V4SF "V2DI")
12522                        (V8SI "V4DI") (V8SF "V4DI")])
12523 (define_mode_attr VEC_GATHER_SRCDI
12524                       [(V2DI "V2DI") (V2DF "V2DF")
12525                        (V4DI "V4DI") (V4DF "V4DF")
12526                        (V4SI "V4SI") (V4SF "V4SF")
12527                        (V8SI "V4SI") (V8SF "V4SF")])
12528
12529 (define_expand "avx2_gathersi<mode>"
12530   [(parallel [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "")
12531                    (unspec:VEC_GATHER_MODE
12532                      [(match_operand:VEC_GATHER_MODE 1 "register_operand" "")
12533                       (mem:<ssescalarmode>
12534                         (match_par_dup 7
12535                           [(match_operand 2 "vsib_address_operand" "")
12536                            (match_operand:<VEC_GATHER_IDXSI>
12537                               3 "register_operand" "")
12538                            (match_operand:SI 5 "const1248_operand " "")]))
12539                       (mem:BLK (scratch))
12540                       (match_operand:VEC_GATHER_MODE 4 "register_operand" "")]
12541                      UNSPEC_GATHER))
12542               (clobber (match_scratch:VEC_GATHER_MODE 6 ""))])]
12543   "TARGET_AVX2"
12544 {
12545   operands[7]
12546     = gen_rtx_UNSPEC (Pmode, gen_rtvec (3, operands[2], operands[3],
12547                                         operands[5]), UNSPEC_VSIBADDR);
12548 })
12549
12550 (define_insn "*avx2_gathersi<mode>"
12551   [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "=&x")
12552         (unspec:VEC_GATHER_MODE
12553           [(match_operand:VEC_GATHER_MODE 2 "register_operand" "0")
12554            (match_operator:<ssescalarmode> 7 "vsib_mem_operator"
12555              [(unspec:P
12556                 [(match_operand:P 3 "vsib_address_operand" "p")
12557                  (match_operand:<VEC_GATHER_IDXSI> 4 "register_operand" "x")
12558                  (match_operand:SI 6 "const1248_operand" "n")]
12559                 UNSPEC_VSIBADDR)])
12560            (mem:BLK (scratch))
12561            (match_operand:VEC_GATHER_MODE 5 "register_operand" "1")]
12562           UNSPEC_GATHER))
12563    (clobber (match_scratch:VEC_GATHER_MODE 1 "=&x"))]
12564   "TARGET_AVX2"
12565   "v<sseintprefix>gatherd<ssemodesuffix>\t{%1, %7, %0|%0, %7, %1}"
12566   [(set_attr "type" "ssemov")
12567    (set_attr "prefix" "vex")
12568    (set_attr "mode" "<sseinsnmode>")])
12569
12570 (define_insn "*avx2_gathersi<mode>_2"
12571   [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "=&x")
12572         (unspec:VEC_GATHER_MODE
12573           [(pc)
12574            (match_operator:<ssescalarmode> 6 "vsib_mem_operator"
12575              [(unspec:P
12576                 [(match_operand:P 2 "vsib_address_operand" "p")
12577                  (match_operand:<VEC_GATHER_IDXSI> 3 "register_operand" "x")
12578                  (match_operand:SI 5 "const1248_operand" "n")]
12579                 UNSPEC_VSIBADDR)])
12580            (mem:BLK (scratch))
12581            (match_operand:VEC_GATHER_MODE 4 "register_operand" "1")]
12582           UNSPEC_GATHER))
12583    (clobber (match_scratch:VEC_GATHER_MODE 1 "=&x"))]
12584   "TARGET_AVX2"
12585   "v<sseintprefix>gatherd<ssemodesuffix>\t{%1, %6, %0|%0, %6, %1}"
12586   [(set_attr "type" "ssemov")
12587    (set_attr "prefix" "vex")
12588    (set_attr "mode" "<sseinsnmode>")])
12589
12590 (define_expand "avx2_gatherdi<mode>"
12591   [(parallel [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "")
12592                    (unspec:VEC_GATHER_MODE
12593                      [(match_operand:<VEC_GATHER_SRCDI> 1 "register_operand" "")
12594                       (mem:<ssescalarmode>
12595                         (match_par_dup 7
12596                           [(match_operand 2 "vsib_address_operand" "")
12597                            (match_operand:<VEC_GATHER_IDXDI>
12598                               3 "register_operand" "")
12599                            (match_operand:SI 5 "const1248_operand " "")]))
12600                       (mem:BLK (scratch))
12601                       (match_operand:<VEC_GATHER_SRCDI>
12602                         4 "register_operand" "")]
12603                      UNSPEC_GATHER))
12604               (clobber (match_scratch:VEC_GATHER_MODE 6 ""))])]
12605   "TARGET_AVX2"
12606 {
12607   operands[7]
12608     = gen_rtx_UNSPEC (Pmode, gen_rtvec (3, operands[2], operands[3],
12609                                         operands[5]), UNSPEC_VSIBADDR);
12610 })
12611
12612 (define_insn "*avx2_gatherdi<mode>"
12613   [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "=&x")
12614         (unspec:VEC_GATHER_MODE
12615           [(match_operand:<VEC_GATHER_SRCDI> 2 "register_operand" "0")
12616            (match_operator:<ssescalarmode> 7 "vsib_mem_operator"
12617              [(unspec:P
12618                 [(match_operand:P 3 "vsib_address_operand" "p")
12619                  (match_operand:<VEC_GATHER_IDXDI> 4 "register_operand" "x")
12620                  (match_operand:SI 6 "const1248_operand" "n")]
12621                 UNSPEC_VSIBADDR)])
12622            (mem:BLK (scratch))
12623            (match_operand:<VEC_GATHER_SRCDI> 5 "register_operand" "1")]
12624           UNSPEC_GATHER))
12625    (clobber (match_scratch:VEC_GATHER_MODE 1 "=&x"))]
12626   "TARGET_AVX2"
12627   "v<sseintprefix>gatherq<ssemodesuffix>\t{%5, %7, %2|%2, %7, %5}"
12628   [(set_attr "type" "ssemov")
12629    (set_attr "prefix" "vex")
12630    (set_attr "mode" "<sseinsnmode>")])
12631
12632 (define_insn "*avx2_gatherdi<mode>_2"
12633   [(set (match_operand:VEC_GATHER_MODE 0 "register_operand" "=&x")
12634         (unspec:VEC_GATHER_MODE
12635           [(pc)
12636            (match_operator:<ssescalarmode> 6 "vsib_mem_operator"
12637              [(unspec:P
12638                 [(match_operand:P 2 "vsib_address_operand" "p")
12639                  (match_operand:<VEC_GATHER_IDXDI> 3 "register_operand" "x")
12640                  (match_operand:SI 5 "const1248_operand" "n")]
12641                 UNSPEC_VSIBADDR)])
12642            (mem:BLK (scratch))
12643            (match_operand:<VEC_GATHER_SRCDI> 4 "register_operand" "1")]
12644           UNSPEC_GATHER))
12645    (clobber (match_scratch:VEC_GATHER_MODE 1 "=&x"))]
12646   "TARGET_AVX2"
12647 {
12648   if (<MODE>mode != <VEC_GATHER_SRCDI>mode)
12649     return "v<sseintprefix>gatherq<ssemodesuffix>\t{%4, %6, %x0|%x0, %6, %4}";
12650   return "v<sseintprefix>gatherq<ssemodesuffix>\t{%4, %6, %0|%0, %6, %4}";
12651 }
12652   [(set_attr "type" "ssemov")
12653    (set_attr "prefix" "vex")
12654    (set_attr "mode" "<sseinsnmode>")])