1 ;; GCC machine description for MMX and 3dNOW! instructions
2 ;; Copyright (C) 2005-2018 Free Software Foundation, Inc.
4 ;; This file is part of GCC.
6 ;; GCC is free software; you can redistribute it and/or modify
7 ;; it under the terms of the GNU General Public License as published by
8 ;; the Free Software Foundation; either version 3, or (at your option)
11 ;; GCC is distributed in the hope that it will be useful,
12 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
13 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 ;; GNU General Public License for more details.
16 ;; You should have received a copy of the GNU General Public License
17 ;; along with GCC; see the file COPYING3. If not see
18 ;; <http://www.gnu.org/licenses/>.
20 ;; The MMX and 3dNOW! patterns are in the same file because they use
21 ;; the same register file, and 3dNOW! adds a number of extensions to
22 ;; the base integer MMX isa.
24 ;; Note! Except for the basic move instructions, *all* of these
25 ;; patterns are outside the normal optabs namespace. This is because
26 ;; use of these registers requires the insertion of emms or femms
27 ;; instructions to return to normal fpu mode. The compiler doesn't
28 ;; know how to do that itself, which means it's up to the user. Which
29 ;; means that we should never use any of these patterns except at the
30 ;; direction of the user via a builtin.
32 (define_c_enum "unspec" [
41 (define_c_enum "unspecv" [
46 ;; 8 byte integral modes handled by MMX (and by extension, SSE)
47 (define_mode_iterator MMXMODEI [V8QI V4HI V2SI])
48 (define_mode_iterator MMXMODEI8 [V8QI V4HI V2SI V1DI])
50 ;; All 8-byte vector modes handled by MMX
51 (define_mode_iterator MMXMODE [V8QI V4HI V2SI V1DI V2SF])
54 (define_mode_iterator MMXMODE12 [V8QI V4HI])
55 (define_mode_iterator MMXMODE24 [V4HI V2SI])
56 (define_mode_iterator MMXMODE248 [V4HI V2SI V1DI])
58 ;; Mapping from integer vector mode to mnemonic suffix
59 (define_mode_attr mmxvecsize [(V8QI "b") (V4HI "w") (V2SI "d") (V1DI "q")])
61 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
65 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
67 ;; All of these patterns are enabled for MMX as well as 3dNOW.
68 ;; This is essential for maintaining stable calling conventions.
70 (define_expand "mov<mode>"
71 [(set (match_operand:MMXMODE 0 "nonimmediate_operand")
72 (match_operand:MMXMODE 1 "nonimmediate_operand"))]
75 ix86_expand_vector_move (<MODE>mode, operands);
79 (define_insn "*mov<mode>_internal"
80 [(set (match_operand:MMXMODE 0 "nonimmediate_operand"
81 "=r ,o ,r,r ,m ,?!y,!y,?!y,m ,r ,?!y,v,v,v,m,r,v,!y,*x")
82 (match_operand:MMXMODE 1 "nonimm_or_0_operand"
83 "rCo,rC,C,rm,rC,C ,!y,m ,?!y,?!y,r ,C,v,m,v,v,r,*x,!y"))]
85 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
87 switch (get_attr_type (insn))
93 if (get_attr_mode (insn) == MODE_SI)
94 return "mov{l}\t{%1, %k0|%k0, %1}";
96 return "mov{q}\t{%1, %0|%0, %1}";
99 return "pxor\t%0, %0";
102 /* Handle broken assemblers that require movd instead of movq. */
103 if (!HAVE_AS_IX86_INTERUNIT_MOVQ
104 && (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1])))
105 return "movd\t{%1, %0|%0, %1}";
106 return "movq\t{%1, %0|%0, %1}";
109 if (SSE_REG_P (operands[0]))
110 return "movq2dq\t{%1, %0|%0, %1}";
112 return "movdq2q\t{%1, %0|%0, %1}";
115 return standard_sse_constant_opcode (insn, operands);
118 switch (get_attr_mode (insn))
121 /* Handle broken assemblers that require movd instead of movq. */
122 if (!HAVE_AS_IX86_INTERUNIT_MOVQ
123 && (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1])))
124 return "%vmovd\t{%1, %0|%0, %1}";
125 return "%vmovq\t{%1, %0|%0, %1}";
127 return "%vmovdqa\t{%1, %0|%0, %1}";
129 return "vmovdqa64\t{%g1, %g0|%g0, %g1}";
132 if (TARGET_AVX && REG_P (operands[0]))
133 return "vmovlps\t{%1, %0, %0|%0, %0, %1}";
134 return "%vmovlps\t{%1, %0|%0, %1}";
136 return "%vmovaps\t{%1, %0|%0, %1}";
147 (cond [(eq_attr "alternative" "0,1")
148 (const_string "nox64")
149 (eq_attr "alternative" "2,3,4,9,10")
151 (eq_attr "alternative" "15,16")
152 (const_string "x64_sse2")
153 (eq_attr "alternative" "17,18")
154 (const_string "sse2")
158 (cond [(eq_attr "alternative" "0,1")
159 (const_string "multi")
160 (eq_attr "alternative" "2,3,4")
161 (const_string "imov")
162 (eq_attr "alternative" "5")
164 (eq_attr "alternative" "6,7,8,9,10")
165 (const_string "mmxmov")
166 (eq_attr "alternative" "11")
167 (const_string "sselog1")
168 (eq_attr "alternative" "17,18")
169 (const_string "ssecvt")
171 (const_string "ssemov")))
172 (set (attr "prefix_rex")
173 (if_then_else (eq_attr "alternative" "9,10,15,16")
177 (if_then_else (eq_attr "type" "sselog1,ssemov")
178 (const_string "maybe_vex")
179 (const_string "orig")))
180 (set (attr "prefix_data16")
182 (and (eq_attr "type" "ssemov") (eq_attr "mode" "DI"))
186 (cond [(eq_attr "alternative" "2")
188 (eq_attr "alternative" "11,12")
189 (cond [(ior (match_operand 0 "ext_sse_reg_operand")
190 (match_operand 1 "ext_sse_reg_operand"))
192 (match_test "<MODE>mode == V2SFmode")
193 (const_string "V4SF")
194 (ior (not (match_test "TARGET_SSE2"))
195 (match_test "TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL"))
196 (const_string "V4SF")
197 (match_test "TARGET_AVX")
199 (match_test "optimize_function_for_size_p (cfun)")
200 (const_string "V4SF")
204 (and (eq_attr "alternative" "13,14")
205 (ior (match_test "<MODE>mode == V2SFmode")
206 (not (match_test "TARGET_SSE2"))))
207 (const_string "V2SF")
209 (const_string "DI")))
210 (set (attr "preferred_for_speed")
211 (cond [(eq_attr "alternative" "10,15")
212 (symbol_ref "TARGET_INTER_UNIT_MOVES_FROM_VEC")
213 (eq_attr "alternative" "11,16")
214 (symbol_ref "TARGET_INTER_UNIT_MOVES_TO_VEC")
216 (symbol_ref "true")))])
219 [(set (match_operand:MMXMODE 0 "nonimmediate_gr_operand")
220 (match_operand:MMXMODE 1 "nonimmediate_gr_operand"))]
221 "!TARGET_64BIT && reload_completed"
223 "ix86_split_long_move (operands); DONE;")
226 [(set (match_operand:MMXMODE 0 "nonimmediate_gr_operand")
227 (match_operand:MMXMODE 1 "const0_operand"))]
228 "!TARGET_64BIT && reload_completed"
230 "ix86_split_long_move (operands); DONE;")
232 (define_expand "movmisalign<mode>"
233 [(set (match_operand:MMXMODE 0 "nonimmediate_operand")
234 (match_operand:MMXMODE 1 "nonimmediate_operand"))]
237 ix86_expand_vector_move (<MODE>mode, operands);
241 (define_insn "sse_movntq"
242 [(set (match_operand:DI 0 "memory_operand" "=m")
243 (unspec:DI [(match_operand:DI 1 "register_operand" "y")]
245 "TARGET_SSE || TARGET_3DNOW_A"
246 "movntq\t{%1, %0|%0, %1}"
247 [(set_attr "type" "mmxmov")
248 (set_attr "mode" "DI")])
250 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
252 ;; Parallel single-precision floating point arithmetic
254 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
256 (define_expand "mmx_addv2sf3"
257 [(set (match_operand:V2SF 0 "register_operand")
259 (match_operand:V2SF 1 "nonimmediate_operand")
260 (match_operand:V2SF 2 "nonimmediate_operand")))]
262 "ix86_fixup_binary_operands_no_copy (PLUS, V2SFmode, operands);")
264 (define_insn "*mmx_addv2sf3"
265 [(set (match_operand:V2SF 0 "register_operand" "=y")
266 (plus:V2SF (match_operand:V2SF 1 "nonimmediate_operand" "%0")
267 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
268 "TARGET_3DNOW && ix86_binary_operator_ok (PLUS, V2SFmode, operands)"
269 "pfadd\t{%2, %0|%0, %2}"
270 [(set_attr "type" "mmxadd")
271 (set_attr "prefix_extra" "1")
272 (set_attr "mode" "V2SF")])
274 (define_expand "mmx_subv2sf3"
275 [(set (match_operand:V2SF 0 "register_operand")
276 (minus:V2SF (match_operand:V2SF 1 "register_operand")
277 (match_operand:V2SF 2 "nonimmediate_operand")))]
280 (define_expand "mmx_subrv2sf3"
281 [(set (match_operand:V2SF 0 "register_operand")
282 (minus:V2SF (match_operand:V2SF 2 "register_operand")
283 (match_operand:V2SF 1 "nonimmediate_operand")))]
286 (define_insn "*mmx_subv2sf3"
287 [(set (match_operand:V2SF 0 "register_operand" "=y,y")
288 (minus:V2SF (match_operand:V2SF 1 "nonimmediate_operand" "0,ym")
289 (match_operand:V2SF 2 "nonimmediate_operand" "ym,0")))]
290 "TARGET_3DNOW && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
292 pfsub\t{%2, %0|%0, %2}
293 pfsubr\t{%1, %0|%0, %1}"
294 [(set_attr "type" "mmxadd")
295 (set_attr "prefix_extra" "1")
296 (set_attr "mode" "V2SF")])
298 (define_expand "mmx_mulv2sf3"
299 [(set (match_operand:V2SF 0 "register_operand")
300 (mult:V2SF (match_operand:V2SF 1 "nonimmediate_operand")
301 (match_operand:V2SF 2 "nonimmediate_operand")))]
303 "ix86_fixup_binary_operands_no_copy (MULT, V2SFmode, operands);")
305 (define_insn "*mmx_mulv2sf3"
306 [(set (match_operand:V2SF 0 "register_operand" "=y")
307 (mult:V2SF (match_operand:V2SF 1 "nonimmediate_operand" "%0")
308 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
309 "TARGET_3DNOW && ix86_binary_operator_ok (MULT, V2SFmode, operands)"
310 "pfmul\t{%2, %0|%0, %2}"
311 [(set_attr "type" "mmxmul")
312 (set_attr "prefix_extra" "1")
313 (set_attr "mode" "V2SF")])
315 (define_expand "mmx_<code>v2sf3"
316 [(set (match_operand:V2SF 0 "register_operand")
318 (match_operand:V2SF 1 "nonimmediate_operand")
319 (match_operand:V2SF 2 "nonimmediate_operand")))]
322 if (!flag_finite_math_only || flag_signed_zeros)
324 operands[1] = force_reg (V2SFmode, operands[1]);
325 emit_insn (gen_mmx_ieee_<maxmin_float>v2sf3
326 (operands[0], operands[1], operands[2]));
330 ix86_fixup_binary_operands_no_copy (<CODE>, V2SFmode, operands);
333 ;; These versions of the min/max patterns are intentionally ignorant of
334 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
335 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
336 ;; are undefined in this condition, we're certain this is correct.
338 (define_insn "*mmx_<code>v2sf3"
339 [(set (match_operand:V2SF 0 "register_operand" "=y")
341 (match_operand:V2SF 1 "nonimmediate_operand" "%0")
342 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
343 "TARGET_3DNOW && ix86_binary_operator_ok (<CODE>, V2SFmode, operands)"
344 "pf<maxmin_float>\t{%2, %0|%0, %2}"
345 [(set_attr "type" "mmxadd")
346 (set_attr "prefix_extra" "1")
347 (set_attr "mode" "V2SF")])
349 ;; These versions of the min/max patterns implement exactly the operations
350 ;; min = (op1 < op2 ? op1 : op2)
351 ;; max = (!(op1 < op2) ? op1 : op2)
352 ;; Their operands are not commutative, and thus they may be used in the
353 ;; presence of -0.0 and NaN.
355 (define_insn "mmx_ieee_<ieee_maxmin>v2sf3"
356 [(set (match_operand:V2SF 0 "register_operand" "=y")
358 [(match_operand:V2SF 1 "register_operand" "0")
359 (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
362 "pf<ieee_maxmin>\t{%2, %0|%0, %2}"
363 [(set_attr "type" "mmxadd")
364 (set_attr "prefix_extra" "1")
365 (set_attr "mode" "V2SF")])
367 (define_insn "mmx_rcpv2sf2"
368 [(set (match_operand:V2SF 0 "register_operand" "=y")
369 (unspec:V2SF [(match_operand:V2SF 1 "nonimmediate_operand" "ym")]
372 "pfrcp\t{%1, %0|%0, %1}"
373 [(set_attr "type" "mmx")
374 (set_attr "prefix_extra" "1")
375 (set_attr "mode" "V2SF")])
377 (define_insn "mmx_rcpit1v2sf3"
378 [(set (match_operand:V2SF 0 "register_operand" "=y")
379 (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
380 (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
383 "pfrcpit1\t{%2, %0|%0, %2}"
384 [(set_attr "type" "mmx")
385 (set_attr "prefix_extra" "1")
386 (set_attr "mode" "V2SF")])
388 (define_insn "mmx_rcpit2v2sf3"
389 [(set (match_operand:V2SF 0 "register_operand" "=y")
390 (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
391 (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
394 "pfrcpit2\t{%2, %0|%0, %2}"
395 [(set_attr "type" "mmx")
396 (set_attr "prefix_extra" "1")
397 (set_attr "mode" "V2SF")])
399 (define_insn "mmx_rsqrtv2sf2"
400 [(set (match_operand:V2SF 0 "register_operand" "=y")
401 (unspec:V2SF [(match_operand:V2SF 1 "nonimmediate_operand" "ym")]
404 "pfrsqrt\t{%1, %0|%0, %1}"
405 [(set_attr "type" "mmx")
406 (set_attr "prefix_extra" "1")
407 (set_attr "mode" "V2SF")])
409 (define_insn "mmx_rsqit1v2sf3"
410 [(set (match_operand:V2SF 0 "register_operand" "=y")
411 (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
412 (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
415 "pfrsqit1\t{%2, %0|%0, %2}"
416 [(set_attr "type" "mmx")
417 (set_attr "prefix_extra" "1")
418 (set_attr "mode" "V2SF")])
420 (define_insn "mmx_haddv2sf3"
421 [(set (match_operand:V2SF 0 "register_operand" "=y")
425 (match_operand:V2SF 1 "register_operand" "0")
426 (parallel [(const_int 0)]))
427 (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
430 (match_operand:V2SF 2 "nonimmediate_operand" "ym")
431 (parallel [(const_int 0)]))
432 (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))))]
434 "pfacc\t{%2, %0|%0, %2}"
435 [(set_attr "type" "mmxadd")
436 (set_attr "prefix_extra" "1")
437 (set_attr "mode" "V2SF")])
439 (define_insn "mmx_hsubv2sf3"
440 [(set (match_operand:V2SF 0 "register_operand" "=y")
444 (match_operand:V2SF 1 "register_operand" "0")
445 (parallel [(const_int 0)]))
446 (vec_select:SF (match_dup 1) (parallel [(const_int 1)])))
449 (match_operand:V2SF 2 "nonimmediate_operand" "ym")
450 (parallel [(const_int 0)]))
451 (vec_select:SF (match_dup 2) (parallel [(const_int 1)])))))]
453 "pfnacc\t{%2, %0|%0, %2}"
454 [(set_attr "type" "mmxadd")
455 (set_attr "prefix_extra" "1")
456 (set_attr "mode" "V2SF")])
458 (define_insn "mmx_addsubv2sf3"
459 [(set (match_operand:V2SF 0 "register_operand" "=y")
462 (match_operand:V2SF 1 "register_operand" "0")
463 (match_operand:V2SF 2 "nonimmediate_operand" "ym"))
464 (minus:V2SF (match_dup 1) (match_dup 2))
467 "pfpnacc\t{%2, %0|%0, %2}"
468 [(set_attr "type" "mmxadd")
469 (set_attr "prefix_extra" "1")
470 (set_attr "mode" "V2SF")])
472 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
474 ;; Parallel single-precision floating point comparisons
476 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
478 (define_expand "mmx_eqv2sf3"
479 [(set (match_operand:V2SI 0 "register_operand")
480 (eq:V2SI (match_operand:V2SF 1 "nonimmediate_operand")
481 (match_operand:V2SF 2 "nonimmediate_operand")))]
483 "ix86_fixup_binary_operands_no_copy (EQ, V2SFmode, operands);")
485 (define_insn "*mmx_eqv2sf3"
486 [(set (match_operand:V2SI 0 "register_operand" "=y")
487 (eq:V2SI (match_operand:V2SF 1 "nonimmediate_operand" "%0")
488 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
489 "TARGET_3DNOW && ix86_binary_operator_ok (EQ, V2SFmode, operands)"
490 "pfcmpeq\t{%2, %0|%0, %2}"
491 [(set_attr "type" "mmxcmp")
492 (set_attr "prefix_extra" "1")
493 (set_attr "mode" "V2SF")])
495 (define_insn "mmx_gtv2sf3"
496 [(set (match_operand:V2SI 0 "register_operand" "=y")
497 (gt:V2SI (match_operand:V2SF 1 "register_operand" "0")
498 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
500 "pfcmpgt\t{%2, %0|%0, %2}"
501 [(set_attr "type" "mmxcmp")
502 (set_attr "prefix_extra" "1")
503 (set_attr "mode" "V2SF")])
505 (define_insn "mmx_gev2sf3"
506 [(set (match_operand:V2SI 0 "register_operand" "=y")
507 (ge:V2SI (match_operand:V2SF 1 "register_operand" "0")
508 (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
510 "pfcmpge\t{%2, %0|%0, %2}"
511 [(set_attr "type" "mmxcmp")
512 (set_attr "prefix_extra" "1")
513 (set_attr "mode" "V2SF")])
515 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
517 ;; Parallel single-precision floating point conversion operations
519 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
521 (define_insn "mmx_pf2id"
522 [(set (match_operand:V2SI 0 "register_operand" "=y")
523 (fix:V2SI (match_operand:V2SF 1 "nonimmediate_operand" "ym")))]
525 "pf2id\t{%1, %0|%0, %1}"
526 [(set_attr "type" "mmxcvt")
527 (set_attr "prefix_extra" "1")
528 (set_attr "mode" "V2SF")])
530 (define_insn "mmx_pf2iw"
531 [(set (match_operand:V2SI 0 "register_operand" "=y")
535 (match_operand:V2SF 1 "nonimmediate_operand" "ym")))))]
537 "pf2iw\t{%1, %0|%0, %1}"
538 [(set_attr "type" "mmxcvt")
539 (set_attr "prefix_extra" "1")
540 (set_attr "mode" "V2SF")])
542 (define_insn "mmx_pi2fw"
543 [(set (match_operand:V2SF 0 "register_operand" "=y")
547 (match_operand:V2SI 1 "nonimmediate_operand" "ym")))))]
549 "pi2fw\t{%1, %0|%0, %1}"
550 [(set_attr "type" "mmxcvt")
551 (set_attr "prefix_extra" "1")
552 (set_attr "mode" "V2SF")])
554 (define_insn "mmx_floatv2si2"
555 [(set (match_operand:V2SF 0 "register_operand" "=y")
556 (float:V2SF (match_operand:V2SI 1 "nonimmediate_operand" "ym")))]
558 "pi2fd\t{%1, %0|%0, %1}"
559 [(set_attr "type" "mmxcvt")
560 (set_attr "prefix_extra" "1")
561 (set_attr "mode" "V2SF")])
563 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
565 ;; Parallel single-precision floating point element swizzling
567 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
569 (define_insn "mmx_pswapdv2sf2"
570 [(set (match_operand:V2SF 0 "register_operand" "=y")
571 (vec_select:V2SF (match_operand:V2SF 1 "nonimmediate_operand" "ym")
572 (parallel [(const_int 1) (const_int 0)])))]
574 "pswapd\t{%1, %0|%0, %1}"
575 [(set_attr "type" "mmxcvt")
576 (set_attr "prefix_extra" "1")
577 (set_attr "mode" "V2SF")])
579 (define_insn "*vec_dupv2sf"
580 [(set (match_operand:V2SF 0 "register_operand" "=y")
582 (match_operand:SF 1 "register_operand" "0")))]
585 [(set_attr "type" "mmxcvt")
586 (set_attr "mode" "DI")])
588 (define_insn "*mmx_concatv2sf"
589 [(set (match_operand:V2SF 0 "register_operand" "=y,y")
591 (match_operand:SF 1 "nonimmediate_operand" " 0,rm")
592 (match_operand:SF 2 "nonimm_or_0_operand" "ym,C")))]
593 "TARGET_MMX && !TARGET_SSE"
595 punpckldq\t{%2, %0|%0, %2}
596 movd\t{%1, %0|%0, %1}"
597 [(set_attr "type" "mmxcvt,mmxmov")
598 (set_attr "mode" "DI")])
600 (define_expand "vec_setv2sf"
601 [(match_operand:V2SF 0 "register_operand")
602 (match_operand:SF 1 "register_operand")
603 (match_operand 2 "const_int_operand")]
606 ix86_expand_vector_set (false, operands[0], operands[1],
607 INTVAL (operands[2]));
611 ;; Avoid combining registers from different units in a single alternative,
612 ;; see comment above inline_secondary_memory_needed function in i386.c
613 (define_insn_and_split "*vec_extractv2sf_0"
614 [(set (match_operand:SF 0 "nonimmediate_operand" "=x, m,y ,m,f,r")
616 (match_operand:V2SF 1 "nonimmediate_operand" " xm,x,ym,y,m,m")
617 (parallel [(const_int 0)])))]
618 "TARGET_MMX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
620 "&& reload_completed"
621 [(set (match_dup 0) (match_dup 1))]
622 "operands[1] = gen_lowpart (SFmode, operands[1]);")
624 ;; Avoid combining registers from different units in a single alternative,
625 ;; see comment above inline_secondary_memory_needed function in i386.c
626 (define_insn "*vec_extractv2sf_1"
627 [(set (match_operand:SF 0 "nonimmediate_operand" "=y,x,x,y,x,f,r")
629 (match_operand:V2SF 1 "nonimmediate_operand" " 0,x,x,o,o,o,o")
630 (parallel [(const_int 1)])))]
631 "TARGET_MMX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
634 %vmovshdup\t{%1, %0|%0, %1}
635 shufps\t{$0xe5, %1, %0|%0, %1, 0xe5}
640 [(set_attr "isa" "*,sse3,noavx,*,*,*,*")
641 (set_attr "type" "mmxcvt,sse,sseshuf1,mmxmov,ssemov,fmov,imov")
642 (set (attr "length_immediate")
643 (if_then_else (eq_attr "alternative" "2")
646 (set (attr "prefix_rep")
647 (if_then_else (eq_attr "alternative" "1")
650 (set_attr "prefix" "orig,maybe_vex,orig,orig,orig,orig,orig")
651 (set_attr "mode" "DI,V4SF,V4SF,SF,SF,SF,SF")])
654 [(set (match_operand:SF 0 "register_operand")
656 (match_operand:V2SF 1 "memory_operand")
657 (parallel [(const_int 1)])))]
658 "TARGET_MMX && reload_completed"
659 [(set (match_dup 0) (match_dup 1))]
660 "operands[1] = adjust_address (operands[1], SFmode, 4);")
662 (define_expand "vec_extractv2sfsf"
663 [(match_operand:SF 0 "register_operand")
664 (match_operand:V2SF 1 "register_operand")
665 (match_operand 2 "const_int_operand")]
668 ix86_expand_vector_extract (false, operands[0], operands[1],
669 INTVAL (operands[2]));
673 (define_expand "vec_initv2sfsf"
674 [(match_operand:V2SF 0 "register_operand")
678 ix86_expand_vector_init (false, operands[0], operands[1]);
682 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
684 ;; Parallel integral arithmetic
686 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
688 (define_expand "mmx_<plusminus_insn><mode>3"
689 [(set (match_operand:MMXMODEI8 0 "register_operand")
691 (match_operand:MMXMODEI8 1 "nonimmediate_operand")
692 (match_operand:MMXMODEI8 2 "nonimmediate_operand")))]
693 "TARGET_MMX || (TARGET_SSE2 && <MODE>mode == V1DImode)"
694 "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
696 (define_insn "*mmx_<plusminus_insn><mode>3"
697 [(set (match_operand:MMXMODEI8 0 "register_operand" "=y")
699 (match_operand:MMXMODEI8 1 "nonimmediate_operand" "<comm>0")
700 (match_operand:MMXMODEI8 2 "nonimmediate_operand" "ym")))]
701 "(TARGET_MMX || (TARGET_SSE2 && <MODE>mode == V1DImode))
702 && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
703 "p<plusminus_mnemonic><mmxvecsize>\t{%2, %0|%0, %2}"
704 [(set_attr "type" "mmxadd")
705 (set_attr "mode" "DI")])
707 (define_expand "mmx_<plusminus_insn><mode>3"
708 [(set (match_operand:MMXMODE12 0 "register_operand")
709 (sat_plusminus:MMXMODE12
710 (match_operand:MMXMODE12 1 "nonimmediate_operand")
711 (match_operand:MMXMODE12 2 "nonimmediate_operand")))]
713 "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
715 (define_insn "*mmx_<plusminus_insn><mode>3"
716 [(set (match_operand:MMXMODE12 0 "register_operand" "=y")
717 (sat_plusminus:MMXMODE12
718 (match_operand:MMXMODE12 1 "nonimmediate_operand" "<comm>0")
719 (match_operand:MMXMODE12 2 "nonimmediate_operand" "ym")))]
720 "TARGET_MMX && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
721 "p<plusminus_mnemonic><mmxvecsize>\t{%2, %0|%0, %2}"
722 [(set_attr "type" "mmxadd")
723 (set_attr "mode" "DI")])
725 (define_expand "mmx_mulv4hi3"
726 [(set (match_operand:V4HI 0 "register_operand")
727 (mult:V4HI (match_operand:V4HI 1 "nonimmediate_operand")
728 (match_operand:V4HI 2 "nonimmediate_operand")))]
730 "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
732 (define_insn "*mmx_mulv4hi3"
733 [(set (match_operand:V4HI 0 "register_operand" "=y")
734 (mult:V4HI (match_operand:V4HI 1 "nonimmediate_operand" "%0")
735 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
736 "TARGET_MMX && ix86_binary_operator_ok (MULT, V4HImode, operands)"
737 "pmullw\t{%2, %0|%0, %2}"
738 [(set_attr "type" "mmxmul")
739 (set_attr "mode" "DI")])
741 (define_expand "mmx_smulv4hi3_highpart"
742 [(set (match_operand:V4HI 0 "register_operand")
747 (match_operand:V4HI 1 "nonimmediate_operand"))
749 (match_operand:V4HI 2 "nonimmediate_operand")))
752 "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
754 (define_insn "*mmx_smulv4hi3_highpart"
755 [(set (match_operand:V4HI 0 "register_operand" "=y")
760 (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
762 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
764 "TARGET_MMX && ix86_binary_operator_ok (MULT, V4HImode, operands)"
765 "pmulhw\t{%2, %0|%0, %2}"
766 [(set_attr "type" "mmxmul")
767 (set_attr "mode" "DI")])
769 (define_expand "mmx_umulv4hi3_highpart"
770 [(set (match_operand:V4HI 0 "register_operand")
775 (match_operand:V4HI 1 "nonimmediate_operand"))
777 (match_operand:V4HI 2 "nonimmediate_operand")))
779 "TARGET_SSE || TARGET_3DNOW_A"
780 "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
782 (define_insn "*mmx_umulv4hi3_highpart"
783 [(set (match_operand:V4HI 0 "register_operand" "=y")
788 (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
790 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
792 "(TARGET_SSE || TARGET_3DNOW_A)
793 && ix86_binary_operator_ok (MULT, V4HImode, operands)"
794 "pmulhuw\t{%2, %0|%0, %2}"
795 [(set_attr "type" "mmxmul")
796 (set_attr "mode" "DI")])
798 (define_expand "mmx_pmaddwd"
799 [(set (match_operand:V2SI 0 "register_operand")
804 (match_operand:V4HI 1 "nonimmediate_operand")
805 (parallel [(const_int 0) (const_int 2)])))
808 (match_operand:V4HI 2 "nonimmediate_operand")
809 (parallel [(const_int 0) (const_int 2)]))))
812 (vec_select:V2HI (match_dup 1)
813 (parallel [(const_int 1) (const_int 3)])))
815 (vec_select:V2HI (match_dup 2)
816 (parallel [(const_int 1) (const_int 3)]))))))]
818 "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
820 (define_insn "*mmx_pmaddwd"
821 [(set (match_operand:V2SI 0 "register_operand" "=y")
826 (match_operand:V4HI 1 "nonimmediate_operand" "%0")
827 (parallel [(const_int 0) (const_int 2)])))
830 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
831 (parallel [(const_int 0) (const_int 2)]))))
834 (vec_select:V2HI (match_dup 1)
835 (parallel [(const_int 1) (const_int 3)])))
837 (vec_select:V2HI (match_dup 2)
838 (parallel [(const_int 1) (const_int 3)]))))))]
839 "TARGET_MMX && ix86_binary_operator_ok (MULT, V4HImode, operands)"
840 "pmaddwd\t{%2, %0|%0, %2}"
841 [(set_attr "type" "mmxmul")
842 (set_attr "mode" "DI")])
844 (define_expand "mmx_pmulhrwv4hi3"
845 [(set (match_operand:V4HI 0 "register_operand")
851 (match_operand:V4HI 1 "nonimmediate_operand"))
853 (match_operand:V4HI 2 "nonimmediate_operand")))
854 (const_vector:V4SI [(const_int 32768) (const_int 32768)
855 (const_int 32768) (const_int 32768)]))
858 "ix86_fixup_binary_operands_no_copy (MULT, V4HImode, operands);")
860 (define_insn "*mmx_pmulhrwv4hi3"
861 [(set (match_operand:V4HI 0 "register_operand" "=y")
867 (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
869 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
870 (const_vector:V4SI [(const_int 32768) (const_int 32768)
871 (const_int 32768) (const_int 32768)]))
873 "TARGET_3DNOW && ix86_binary_operator_ok (MULT, V4HImode, operands)"
874 "pmulhrw\t{%2, %0|%0, %2}"
875 [(set_attr "type" "mmxmul")
876 (set_attr "prefix_extra" "1")
877 (set_attr "mode" "DI")])
879 (define_expand "sse2_umulv1siv1di3"
880 [(set (match_operand:V1DI 0 "register_operand")
884 (match_operand:V2SI 1 "nonimmediate_operand")
885 (parallel [(const_int 0)])))
888 (match_operand:V2SI 2 "nonimmediate_operand")
889 (parallel [(const_int 0)])))))]
891 "ix86_fixup_binary_operands_no_copy (MULT, V2SImode, operands);")
893 (define_insn "*sse2_umulv1siv1di3"
894 [(set (match_operand:V1DI 0 "register_operand" "=y")
898 (match_operand:V2SI 1 "nonimmediate_operand" "%0")
899 (parallel [(const_int 0)])))
902 (match_operand:V2SI 2 "nonimmediate_operand" "ym")
903 (parallel [(const_int 0)])))))]
904 "TARGET_SSE2 && ix86_binary_operator_ok (MULT, V2SImode, operands)"
905 "pmuludq\t{%2, %0|%0, %2}"
906 [(set_attr "type" "mmxmul")
907 (set_attr "mode" "DI")])
909 (define_expand "mmx_<code>v4hi3"
910 [(set (match_operand:V4HI 0 "register_operand")
912 (match_operand:V4HI 1 "nonimmediate_operand")
913 (match_operand:V4HI 2 "nonimmediate_operand")))]
914 "TARGET_SSE || TARGET_3DNOW_A"
915 "ix86_fixup_binary_operands_no_copy (<CODE>, V4HImode, operands);")
917 (define_insn "*mmx_<code>v4hi3"
918 [(set (match_operand:V4HI 0 "register_operand" "=y")
920 (match_operand:V4HI 1 "nonimmediate_operand" "%0")
921 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
922 "(TARGET_SSE || TARGET_3DNOW_A)
923 && ix86_binary_operator_ok (<CODE>, V4HImode, operands)"
924 "p<maxmin_int>w\t{%2, %0|%0, %2}"
925 [(set_attr "type" "mmxadd")
926 (set_attr "mode" "DI")])
928 (define_expand "mmx_<code>v8qi3"
929 [(set (match_operand:V8QI 0 "register_operand")
931 (match_operand:V8QI 1 "nonimmediate_operand")
932 (match_operand:V8QI 2 "nonimmediate_operand")))]
933 "TARGET_SSE || TARGET_3DNOW_A"
934 "ix86_fixup_binary_operands_no_copy (<CODE>, V8QImode, operands);")
936 (define_insn "*mmx_<code>v8qi3"
937 [(set (match_operand:V8QI 0 "register_operand" "=y")
939 (match_operand:V8QI 1 "nonimmediate_operand" "%0")
940 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
941 "(TARGET_SSE || TARGET_3DNOW_A)
942 && ix86_binary_operator_ok (<CODE>, V8QImode, operands)"
943 "p<maxmin_int>b\t{%2, %0|%0, %2}"
944 [(set_attr "type" "mmxadd")
945 (set_attr "mode" "DI")])
947 (define_insn "mmx_ashr<mode>3"
948 [(set (match_operand:MMXMODE24 0 "register_operand" "=y")
950 (match_operand:MMXMODE24 1 "register_operand" "0")
951 (match_operand:DI 2 "nonmemory_operand" "yN")))]
953 "psra<mmxvecsize>\t{%2, %0|%0, %2}"
954 [(set_attr "type" "mmxshft")
955 (set (attr "length_immediate")
956 (if_then_else (match_operand 2 "const_int_operand")
959 (set_attr "mode" "DI")])
961 (define_insn "mmx_<shift_insn><mode>3"
962 [(set (match_operand:MMXMODE248 0 "register_operand" "=y")
963 (any_lshift:MMXMODE248
964 (match_operand:MMXMODE248 1 "register_operand" "0")
965 (match_operand:DI 2 "nonmemory_operand" "yN")))]
967 "p<vshift><mmxvecsize>\t{%2, %0|%0, %2}"
968 [(set_attr "type" "mmxshft")
969 (set (attr "length_immediate")
970 (if_then_else (match_operand 2 "const_int_operand")
973 (set_attr "mode" "DI")])
975 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
977 ;; Parallel integral comparisons
979 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
981 (define_expand "mmx_eq<mode>3"
982 [(set (match_operand:MMXMODEI 0 "register_operand")
984 (match_operand:MMXMODEI 1 "nonimmediate_operand")
985 (match_operand:MMXMODEI 2 "nonimmediate_operand")))]
987 "ix86_fixup_binary_operands_no_copy (EQ, <MODE>mode, operands);")
989 (define_insn "*mmx_eq<mode>3"
990 [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
992 (match_operand:MMXMODEI 1 "nonimmediate_operand" "%0")
993 (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")))]
994 "TARGET_MMX && ix86_binary_operator_ok (EQ, <MODE>mode, operands)"
995 "pcmpeq<mmxvecsize>\t{%2, %0|%0, %2}"
996 [(set_attr "type" "mmxcmp")
997 (set_attr "mode" "DI")])
999 (define_insn "mmx_gt<mode>3"
1000 [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
1002 (match_operand:MMXMODEI 1 "register_operand" "0")
1003 (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")))]
1005 "pcmpgt<mmxvecsize>\t{%2, %0|%0, %2}"
1006 [(set_attr "type" "mmxcmp")
1007 (set_attr "mode" "DI")])
1009 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1011 ;; Parallel integral logical operations
1013 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1015 (define_insn "mmx_andnot<mode>3"
1016 [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
1018 (not:MMXMODEI (match_operand:MMXMODEI 1 "register_operand" "0"))
1019 (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")))]
1021 "pandn\t{%2, %0|%0, %2}"
1022 [(set_attr "type" "mmxadd")
1023 (set_attr "mode" "DI")])
1025 (define_expand "mmx_<code><mode>3"
1026 [(set (match_operand:MMXMODEI 0 "register_operand")
1028 (match_operand:MMXMODEI 1 "nonimmediate_operand")
1029 (match_operand:MMXMODEI 2 "nonimmediate_operand")))]
1031 "ix86_fixup_binary_operands_no_copy (<CODE>, <MODE>mode, operands);")
1033 (define_insn "*mmx_<code><mode>3"
1034 [(set (match_operand:MMXMODEI 0 "register_operand" "=y")
1036 (match_operand:MMXMODEI 1 "nonimmediate_operand" "%0")
1037 (match_operand:MMXMODEI 2 "nonimmediate_operand" "ym")))]
1038 "TARGET_MMX && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
1039 "p<logic>\t{%2, %0|%0, %2}"
1040 [(set_attr "type" "mmxadd")
1041 (set_attr "mode" "DI")])
1043 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1045 ;; Parallel integral element swizzling
1047 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1049 (define_insn "mmx_packsswb"
1050 [(set (match_operand:V8QI 0 "register_operand" "=y")
1053 (match_operand:V4HI 1 "register_operand" "0"))
1055 (match_operand:V4HI 2 "nonimmediate_operand" "ym"))))]
1057 "packsswb\t{%2, %0|%0, %2}"
1058 [(set_attr "type" "mmxshft")
1059 (set_attr "mode" "DI")])
1061 (define_insn "mmx_packssdw"
1062 [(set (match_operand:V4HI 0 "register_operand" "=y")
1065 (match_operand:V2SI 1 "register_operand" "0"))
1067 (match_operand:V2SI 2 "nonimmediate_operand" "ym"))))]
1069 "packssdw\t{%2, %0|%0, %2}"
1070 [(set_attr "type" "mmxshft")
1071 (set_attr "mode" "DI")])
1073 (define_insn "mmx_packuswb"
1074 [(set (match_operand:V8QI 0 "register_operand" "=y")
1077 (match_operand:V4HI 1 "register_operand" "0"))
1079 (match_operand:V4HI 2 "nonimmediate_operand" "ym"))))]
1081 "packuswb\t{%2, %0|%0, %2}"
1082 [(set_attr "type" "mmxshft")
1083 (set_attr "mode" "DI")])
1085 (define_insn "mmx_punpckhbw"
1086 [(set (match_operand:V8QI 0 "register_operand" "=y")
1089 (match_operand:V8QI 1 "register_operand" "0")
1090 (match_operand:V8QI 2 "nonimmediate_operand" "ym"))
1091 (parallel [(const_int 4) (const_int 12)
1092 (const_int 5) (const_int 13)
1093 (const_int 6) (const_int 14)
1094 (const_int 7) (const_int 15)])))]
1096 "punpckhbw\t{%2, %0|%0, %2}"
1097 [(set_attr "type" "mmxcvt")
1098 (set_attr "mode" "DI")])
1100 (define_insn "mmx_punpcklbw"
1101 [(set (match_operand:V8QI 0 "register_operand" "=y")
1104 (match_operand:V8QI 1 "register_operand" "0")
1105 (match_operand:V8QI 2 "nonimmediate_operand" "ym"))
1106 (parallel [(const_int 0) (const_int 8)
1107 (const_int 1) (const_int 9)
1108 (const_int 2) (const_int 10)
1109 (const_int 3) (const_int 11)])))]
1111 "punpcklbw\t{%2, %0|%0, %k2}"
1112 [(set_attr "type" "mmxcvt")
1113 (set_attr "mode" "DI")])
1115 (define_insn "mmx_punpckhwd"
1116 [(set (match_operand:V4HI 0 "register_operand" "=y")
1119 (match_operand:V4HI 1 "register_operand" "0")
1120 (match_operand:V4HI 2 "nonimmediate_operand" "ym"))
1121 (parallel [(const_int 2) (const_int 6)
1122 (const_int 3) (const_int 7)])))]
1124 "punpckhwd\t{%2, %0|%0, %2}"
1125 [(set_attr "type" "mmxcvt")
1126 (set_attr "mode" "DI")])
1128 (define_insn "mmx_punpcklwd"
1129 [(set (match_operand:V4HI 0 "register_operand" "=y")
1132 (match_operand:V4HI 1 "register_operand" "0")
1133 (match_operand:V4HI 2 "nonimmediate_operand" "ym"))
1134 (parallel [(const_int 0) (const_int 4)
1135 (const_int 1) (const_int 5)])))]
1137 "punpcklwd\t{%2, %0|%0, %k2}"
1138 [(set_attr "type" "mmxcvt")
1139 (set_attr "mode" "DI")])
1141 (define_insn "mmx_punpckhdq"
1142 [(set (match_operand:V2SI 0 "register_operand" "=y")
1145 (match_operand:V2SI 1 "register_operand" "0")
1146 (match_operand:V2SI 2 "nonimmediate_operand" "ym"))
1147 (parallel [(const_int 1)
1150 "punpckhdq\t{%2, %0|%0, %2}"
1151 [(set_attr "type" "mmxcvt")
1152 (set_attr "mode" "DI")])
1154 (define_insn "mmx_punpckldq"
1155 [(set (match_operand:V2SI 0 "register_operand" "=y")
1158 (match_operand:V2SI 1 "register_operand" "0")
1159 (match_operand:V2SI 2 "nonimmediate_operand" "ym"))
1160 (parallel [(const_int 0)
1163 "punpckldq\t{%2, %0|%0, %k2}"
1164 [(set_attr "type" "mmxcvt")
1165 (set_attr "mode" "DI")])
1167 (define_expand "mmx_pinsrw"
1168 [(set (match_operand:V4HI 0 "register_operand")
1171 (match_operand:SI 2 "nonimmediate_operand"))
1172 (match_operand:V4HI 1 "register_operand")
1173 (match_operand:SI 3 "const_0_to_3_operand")))]
1174 "TARGET_SSE || TARGET_3DNOW_A"
1176 operands[2] = gen_lowpart (HImode, operands[2]);
1177 operands[3] = GEN_INT (1 << INTVAL (operands[3]));
1180 (define_insn "*mmx_pinsrw"
1181 [(set (match_operand:V4HI 0 "register_operand" "=y")
1184 (match_operand:HI 2 "nonimmediate_operand" "rm"))
1185 (match_operand:V4HI 1 "register_operand" "0")
1186 (match_operand:SI 3 "const_int_operand")))]
1187 "(TARGET_SSE || TARGET_3DNOW_A)
1188 && ((unsigned) exact_log2 (INTVAL (operands[3]))
1189 < GET_MODE_NUNITS (V4HImode))"
1191 operands[3] = GEN_INT (exact_log2 (INTVAL (operands[3])));
1192 if (MEM_P (operands[2]))
1193 return "pinsrw\t{%3, %2, %0|%0, %2, %3}";
1195 return "pinsrw\t{%3, %k2, %0|%0, %k2, %3}";
1197 [(set_attr "type" "mmxcvt")
1198 (set_attr "length_immediate" "1")
1199 (set_attr "mode" "DI")])
1201 (define_insn "mmx_pextrw"
1202 [(set (match_operand:SI 0 "register_operand" "=r")
1205 (match_operand:V4HI 1 "register_operand" "y")
1206 (parallel [(match_operand:SI 2 "const_0_to_3_operand" "n")]))))]
1207 "TARGET_SSE || TARGET_3DNOW_A"
1208 "pextrw\t{%2, %1, %0|%0, %1, %2}"
1209 [(set_attr "type" "mmxcvt")
1210 (set_attr "length_immediate" "1")
1211 (set_attr "mode" "DI")])
1213 (define_expand "mmx_pshufw"
1214 [(match_operand:V4HI 0 "register_operand")
1215 (match_operand:V4HI 1 "nonimmediate_operand")
1216 (match_operand:SI 2 "const_int_operand")]
1217 "TARGET_SSE || TARGET_3DNOW_A"
1219 int mask = INTVAL (operands[2]);
1220 emit_insn (gen_mmx_pshufw_1 (operands[0], operands[1],
1221 GEN_INT ((mask >> 0) & 3),
1222 GEN_INT ((mask >> 2) & 3),
1223 GEN_INT ((mask >> 4) & 3),
1224 GEN_INT ((mask >> 6) & 3)));
1228 (define_insn "mmx_pshufw_1"
1229 [(set (match_operand:V4HI 0 "register_operand" "=y")
1231 (match_operand:V4HI 1 "nonimmediate_operand" "ym")
1232 (parallel [(match_operand 2 "const_0_to_3_operand")
1233 (match_operand 3 "const_0_to_3_operand")
1234 (match_operand 4 "const_0_to_3_operand")
1235 (match_operand 5 "const_0_to_3_operand")])))]
1236 "TARGET_SSE || TARGET_3DNOW_A"
1239 mask |= INTVAL (operands[2]) << 0;
1240 mask |= INTVAL (operands[3]) << 2;
1241 mask |= INTVAL (operands[4]) << 4;
1242 mask |= INTVAL (operands[5]) << 6;
1243 operands[2] = GEN_INT (mask);
1245 return "pshufw\t{%2, %1, %0|%0, %1, %2}";
1247 [(set_attr "type" "mmxcvt")
1248 (set_attr "length_immediate" "1")
1249 (set_attr "mode" "DI")])
1251 (define_insn "mmx_pswapdv2si2"
1252 [(set (match_operand:V2SI 0 "register_operand" "=y")
1254 (match_operand:V2SI 1 "nonimmediate_operand" "ym")
1255 (parallel [(const_int 1) (const_int 0)])))]
1257 "pswapd\t{%1, %0|%0, %1}"
1258 [(set_attr "type" "mmxcvt")
1259 (set_attr "prefix_extra" "1")
1260 (set_attr "mode" "DI")])
1262 (define_insn "*vec_dupv4hi"
1263 [(set (match_operand:V4HI 0 "register_operand" "=y")
1266 (match_operand:SI 1 "register_operand" "0"))))]
1267 "TARGET_SSE || TARGET_3DNOW_A"
1268 "pshufw\t{$0, %0, %0|%0, %0, 0}"
1269 [(set_attr "type" "mmxcvt")
1270 (set_attr "length_immediate" "1")
1271 (set_attr "mode" "DI")])
1273 (define_insn "*vec_dupv2si"
1274 [(set (match_operand:V2SI 0 "register_operand" "=y")
1276 (match_operand:SI 1 "register_operand" "0")))]
1279 [(set_attr "type" "mmxcvt")
1280 (set_attr "mode" "DI")])
1282 (define_insn "*mmx_concatv2si"
1283 [(set (match_operand:V2SI 0 "register_operand" "=y,y")
1285 (match_operand:SI 1 "nonimmediate_operand" " 0,rm")
1286 (match_operand:SI 2 "nonimm_or_0_operand" "ym,C")))]
1287 "TARGET_MMX && !TARGET_SSE"
1289 punpckldq\t{%2, %0|%0, %2}
1290 movd\t{%1, %0|%0, %1}"
1291 [(set_attr "type" "mmxcvt,mmxmov")
1292 (set_attr "mode" "DI")])
1294 (define_expand "vec_setv2si"
1295 [(match_operand:V2SI 0 "register_operand")
1296 (match_operand:SI 1 "register_operand")
1297 (match_operand 2 "const_int_operand")]
1300 ix86_expand_vector_set (false, operands[0], operands[1],
1301 INTVAL (operands[2]));
1305 ;; Avoid combining registers from different units in a single alternative,
1306 ;; see comment above inline_secondary_memory_needed function in i386.c
1307 (define_insn_and_split "*vec_extractv2si_0"
1308 [(set (match_operand:SI 0 "nonimmediate_operand" "=x,m,y, m,r")
1310 (match_operand:V2SI 1 "nonimmediate_operand" "xm,x,ym,y,m")
1311 (parallel [(const_int 0)])))]
1312 "TARGET_MMX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1314 "&& reload_completed"
1315 [(set (match_dup 0) (match_dup 1))]
1316 "operands[1] = gen_lowpart (SImode, operands[1]);")
1318 ;; Avoid combining registers from different units in a single alternative,
1319 ;; see comment above inline_secondary_memory_needed function in i386.c
1320 (define_insn "*vec_extractv2si_1"
1321 [(set (match_operand:SI 0 "nonimmediate_operand" "=y,x,x,y,x,r")
1323 (match_operand:V2SI 1 "nonimmediate_operand" " 0,x,x,o,o,o")
1324 (parallel [(const_int 1)])))]
1325 "TARGET_MMX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1328 %vpshufd\t{$0xe5, %1, %0|%0, %1, 0xe5}
1329 shufps\t{$0xe5, %1, %0|%0, %1, 0xe5}
1333 [(set_attr "isa" "*,sse2,noavx,*,*,*")
1334 (set_attr "type" "mmxcvt,sseshuf1,sseshuf1,mmxmov,ssemov,imov")
1335 (set (attr "length_immediate")
1336 (if_then_else (eq_attr "alternative" "1,2")
1338 (const_string "*")))
1339 (set_attr "prefix" "orig,maybe_vex,orig,orig,orig,orig")
1340 (set_attr "mode" "DI,TI,V4SF,SI,SI,SI")])
1343 [(set (match_operand:SI 0 "register_operand")
1345 (match_operand:V2SI 1 "memory_operand")
1346 (parallel [(const_int 1)])))]
1347 "TARGET_MMX && reload_completed"
1348 [(set (match_dup 0) (match_dup 1))]
1349 "operands[1] = adjust_address (operands[1], SImode, 4);")
1351 (define_insn_and_split "*vec_extractv2si_zext_mem"
1352 [(set (match_operand:DI 0 "register_operand" "=y,x,r")
1355 (match_operand:V2SI 1 "memory_operand" "o,o,o")
1356 (parallel [(match_operand:SI 2 "const_0_to_1_operand")]))))]
1357 "TARGET_64BIT && TARGET_MMX"
1359 "&& reload_completed"
1360 [(set (match_dup 0) (zero_extend:DI (match_dup 1)))]
1362 operands[1] = adjust_address (operands[1], SImode, INTVAL (operands[2]) * 4);
1365 (define_expand "vec_extractv2sisi"
1366 [(match_operand:SI 0 "register_operand")
1367 (match_operand:V2SI 1 "register_operand")
1368 (match_operand 2 "const_int_operand")]
1371 ix86_expand_vector_extract (false, operands[0], operands[1],
1372 INTVAL (operands[2]));
1376 (define_expand "vec_initv2sisi"
1377 [(match_operand:V2SI 0 "register_operand")
1381 ix86_expand_vector_init (false, operands[0], operands[1]);
1385 (define_expand "vec_setv4hi"
1386 [(match_operand:V4HI 0 "register_operand")
1387 (match_operand:HI 1 "register_operand")
1388 (match_operand 2 "const_int_operand")]
1391 ix86_expand_vector_set (false, operands[0], operands[1],
1392 INTVAL (operands[2]));
1396 (define_expand "vec_extractv4hihi"
1397 [(match_operand:HI 0 "register_operand")
1398 (match_operand:V4HI 1 "register_operand")
1399 (match_operand 2 "const_int_operand")]
1402 ix86_expand_vector_extract (false, operands[0], operands[1],
1403 INTVAL (operands[2]));
1407 (define_expand "vec_initv4hihi"
1408 [(match_operand:V4HI 0 "register_operand")
1412 ix86_expand_vector_init (false, operands[0], operands[1]);
1416 (define_expand "vec_setv8qi"
1417 [(match_operand:V8QI 0 "register_operand")
1418 (match_operand:QI 1 "register_operand")
1419 (match_operand 2 "const_int_operand")]
1422 ix86_expand_vector_set (false, operands[0], operands[1],
1423 INTVAL (operands[2]));
1427 (define_expand "vec_extractv8qiqi"
1428 [(match_operand:QI 0 "register_operand")
1429 (match_operand:V8QI 1 "register_operand")
1430 (match_operand 2 "const_int_operand")]
1433 ix86_expand_vector_extract (false, operands[0], operands[1],
1434 INTVAL (operands[2]));
1438 (define_expand "vec_initv8qiqi"
1439 [(match_operand:V8QI 0 "register_operand")
1443 ix86_expand_vector_init (false, operands[0], operands[1]);
1447 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1451 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1453 (define_expand "mmx_uavgv8qi3"
1454 [(set (match_operand:V8QI 0 "register_operand")
1460 (match_operand:V8QI 1 "nonimmediate_operand"))
1462 (match_operand:V8QI 2 "nonimmediate_operand")))
1463 (const_vector:V8HI [(const_int 1) (const_int 1)
1464 (const_int 1) (const_int 1)
1465 (const_int 1) (const_int 1)
1466 (const_int 1) (const_int 1)]))
1468 "TARGET_SSE || TARGET_3DNOW"
1469 "ix86_fixup_binary_operands_no_copy (PLUS, V8QImode, operands);")
1471 (define_insn "*mmx_uavgv8qi3"
1472 [(set (match_operand:V8QI 0 "register_operand" "=y")
1478 (match_operand:V8QI 1 "nonimmediate_operand" "%0"))
1480 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))
1481 (const_vector:V8HI [(const_int 1) (const_int 1)
1482 (const_int 1) (const_int 1)
1483 (const_int 1) (const_int 1)
1484 (const_int 1) (const_int 1)]))
1486 "(TARGET_SSE || TARGET_3DNOW)
1487 && ix86_binary_operator_ok (PLUS, V8QImode, operands)"
1489 /* These two instructions have the same operation, but their encoding
1490 is different. Prefer the one that is de facto standard. */
1491 if (TARGET_SSE || TARGET_3DNOW_A)
1492 return "pavgb\t{%2, %0|%0, %2}";
1494 return "pavgusb\t{%2, %0|%0, %2}";
1496 [(set_attr "type" "mmxshft")
1497 (set (attr "prefix_extra")
1499 (not (ior (match_test "TARGET_SSE")
1500 (match_test "TARGET_3DNOW_A")))
1502 (const_string "*")))
1503 (set_attr "mode" "DI")])
1505 (define_expand "mmx_uavgv4hi3"
1506 [(set (match_operand:V4HI 0 "register_operand")
1512 (match_operand:V4HI 1 "nonimmediate_operand"))
1514 (match_operand:V4HI 2 "nonimmediate_operand")))
1515 (const_vector:V4SI [(const_int 1) (const_int 1)
1516 (const_int 1) (const_int 1)]))
1518 "TARGET_SSE || TARGET_3DNOW_A"
1519 "ix86_fixup_binary_operands_no_copy (PLUS, V4HImode, operands);")
1521 (define_insn "*mmx_uavgv4hi3"
1522 [(set (match_operand:V4HI 0 "register_operand" "=y")
1528 (match_operand:V4HI 1 "nonimmediate_operand" "%0"))
1530 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
1531 (const_vector:V4SI [(const_int 1) (const_int 1)
1532 (const_int 1) (const_int 1)]))
1534 "(TARGET_SSE || TARGET_3DNOW_A)
1535 && ix86_binary_operator_ok (PLUS, V4HImode, operands)"
1536 "pavgw\t{%2, %0|%0, %2}"
1537 [(set_attr "type" "mmxshft")
1538 (set_attr "mode" "DI")])
1540 (define_insn "mmx_psadbw"
1541 [(set (match_operand:V1DI 0 "register_operand" "=y")
1542 (unspec:V1DI [(match_operand:V8QI 1 "register_operand" "0")
1543 (match_operand:V8QI 2 "nonimmediate_operand" "ym")]
1545 "TARGET_SSE || TARGET_3DNOW_A"
1546 "psadbw\t{%2, %0|%0, %2}"
1547 [(set_attr "type" "mmxshft")
1548 (set_attr "mode" "DI")])
1550 (define_insn "mmx_pmovmskb"
1551 [(set (match_operand:SI 0 "register_operand" "=r")
1552 (unspec:SI [(match_operand:V8QI 1 "register_operand" "y")]
1554 "TARGET_SSE || TARGET_3DNOW_A"
1555 "pmovmskb\t{%1, %0|%0, %1}"
1556 [(set_attr "type" "mmxcvt")
1557 (set_attr "mode" "DI")])
1559 (define_expand "mmx_maskmovq"
1560 [(set (match_operand:V8QI 0 "memory_operand")
1561 (unspec:V8QI [(match_operand:V8QI 1 "register_operand")
1562 (match_operand:V8QI 2 "register_operand")
1565 "TARGET_SSE || TARGET_3DNOW_A")
1567 (define_insn "*mmx_maskmovq"
1568 [(set (mem:V8QI (match_operand:P 0 "register_operand" "D"))
1569 (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "y")
1570 (match_operand:V8QI 2 "register_operand" "y")
1571 (mem:V8QI (match_dup 0))]
1573 "TARGET_SSE || TARGET_3DNOW_A"
1574 ;; @@@ check ordering of operands in intel/nonintel syntax
1575 "maskmovq\t{%2, %1|%1, %2}"
1576 [(set_attr "type" "mmxcvt")
1577 (set_attr "znver1_decode" "vector")
1578 (set_attr "mode" "DI")])
1580 (define_int_iterator EMMS
1581 [(UNSPECV_EMMS "TARGET_MMX")
1582 (UNSPECV_FEMMS "TARGET_3DNOW")])
1584 (define_int_attr emms
1585 [(UNSPECV_EMMS "emms")
1586 (UNSPECV_FEMMS "femms")])
1588 (define_insn "mmx_<emms>"
1589 [(unspec_volatile [(const_int 0)] EMMS)
1590 (clobber (reg:XF ST0_REG))
1591 (clobber (reg:XF ST1_REG))
1592 (clobber (reg:XF ST2_REG))
1593 (clobber (reg:XF ST3_REG))
1594 (clobber (reg:XF ST4_REG))
1595 (clobber (reg:XF ST5_REG))
1596 (clobber (reg:XF ST6_REG))
1597 (clobber (reg:XF ST7_REG))
1598 (clobber (reg:DI MM0_REG))
1599 (clobber (reg:DI MM1_REG))
1600 (clobber (reg:DI MM2_REG))
1601 (clobber (reg:DI MM3_REG))
1602 (clobber (reg:DI MM4_REG))
1603 (clobber (reg:DI MM5_REG))
1604 (clobber (reg:DI MM6_REG))
1605 (clobber (reg:DI MM7_REG))]
1608 [(set_attr "type" "mmx")
1609 (set_attr "modrm" "0")
1610 (set_attr "memory" "none")])