1 ;; GCC machine description for IA-32 and x86-64.
2 ;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 ;; 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
4 ;; Free Software Foundation, Inc.
5 ;; Mostly by William Schelter.
6 ;; x86_64 support added by Jan Hubicka
8 ;; This file is part of GCC.
10 ;; GCC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 3, or (at your option)
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING3. If not see
22 ;; <http://www.gnu.org/licenses/>. */
24 ;; The original PO technology requires these to be ordered by speed,
25 ;; so that assigner will pick the fastest.
27 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
29 ;; The special asm out single letter directives following a '%' are:
30 ;; L,W,B,Q,S,T -- print the opcode suffix for specified size of operand.
31 ;; C -- print opcode suffix for set/cmov insn.
32 ;; c -- like C, but print reversed condition
33 ;; E,e -- likewise, but for compare-and-branch fused insn.
34 ;; F,f -- likewise, but for floating-point.
35 ;; O -- if HAVE_AS_IX86_CMOV_SUN_SYNTAX, expand to "w.", "l." or "q.",
37 ;; R -- print the prefix for register names.
38 ;; z -- print the opcode suffix for the size of the current operand.
39 ;; Z -- likewise, with special suffixes for x87 instructions.
40 ;; * -- print a star (in certain assembler syntax)
41 ;; A -- print an absolute memory reference.
42 ;; w -- print the operand as if it's a "word" (HImode) even if it isn't.
43 ;; s -- print a shift double count, followed by the assemblers argument
45 ;; b -- print the QImode name of the register for the indicated operand.
46 ;; %b0 would print %al if operands[0] is reg 0.
47 ;; w -- likewise, print the HImode name of the register.
48 ;; k -- likewise, print the SImode name of the register.
49 ;; q -- likewise, print the DImode name of the register.
50 ;; x -- likewise, print the V4SFmode name of the register.
51 ;; t -- likewise, print the V8SFmode name of the register.
52 ;; h -- print the QImode name for a "high" register, either ah, bh, ch or dh.
53 ;; y -- print "st(0)" instead of "st" as a register.
54 ;; d -- print duplicated register operand for AVX instruction.
55 ;; D -- print condition for SSE cmp instruction.
56 ;; P -- if PIC, print an @PLT suffix.
57 ;; X -- don't print any sort of PIC '@' suffix for a symbol.
58 ;; & -- print some in-use local-dynamic symbol name.
59 ;; H -- print a memory address offset by 8; used for sse high-parts
60 ;; Y -- print condition for SSE5 com* instruction.
61 ;; + -- print a branch hint as 'cs' or 'ds' prefix
62 ;; ; -- print a semicolon (after prefixes due to bug in older gas).
67 [; Relocation specifiers
78 (UNSPEC_MACHOPIC_OFFSET 10)
81 (UNSPEC_STACK_ALLOC 11)
83 (UNSPEC_SSE_PROLOGUE_SAVE 13)
87 (UNSPEC_SET_GOT_OFFSET 17)
88 (UNSPEC_MEMORY_BLOCKAGE 18)
93 (UNSPEC_TLS_LD_BASE 22)
96 ; Other random patterns
101 (UNSPEC_ADD_CARRY 34)
104 (UNSPEC_EH_RETURN 37)
105 (UNSPEC_LD_MPIC 38) ; load_macho_picbase
106 (UNSPEC_TRUNC_NOOP 39)
108 ; For SSE/MMX support:
109 (UNSPEC_FIX_NOTRUNC 40)
126 (UNSPEC_MS_TO_SYSV_CALL 48)
128 ; Generic math support
130 (UNSPEC_IEEE_MIN 51) ; not commutative
131 (UNSPEC_IEEE_MAX 52) ; not commutative
146 (UNSPEC_FRNDINT_FLOOR 70)
147 (UNSPEC_FRNDINT_CEIL 71)
148 (UNSPEC_FRNDINT_TRUNC 72)
149 (UNSPEC_FRNDINT_MASK_PM 73)
150 (UNSPEC_FIST_FLOOR 74)
151 (UNSPEC_FIST_CEIL 75)
153 ; x87 Double output FP
154 (UNSPEC_SINCOS_COS 80)
155 (UNSPEC_SINCOS_SIN 81)
156 (UNSPEC_XTRACT_FRACT 84)
157 (UNSPEC_XTRACT_EXP 85)
158 (UNSPEC_FSCALE_FRACT 86)
159 (UNSPEC_FSCALE_EXP 87)
171 (UNSPEC_SP_TLS_SET 102)
172 (UNSPEC_SP_TLS_TEST 103)
182 (UNSPEC_INSERTQI 132)
187 (UNSPEC_INSERTPS 135)
189 (UNSPEC_MOVNTDQA 137)
191 (UNSPEC_PHMINPOSUW 139)
197 (UNSPEC_PCMPESTR 144)
198 (UNSPEC_PCMPISTR 145)
201 (UNSPEC_SSE5_INTRINSIC 150)
202 (UNSPEC_SSE5_UNSIGNED_CMP 151)
203 (UNSPEC_SSE5_TRUEFALSE 152)
204 (UNSPEC_SSE5_PERMUTE 153)
206 (UNSPEC_CVTPH2PS 155)
207 (UNSPEC_CVTPS2PH 156)
211 (UNSPEC_AESENCLAST 160)
213 (UNSPEC_AESDECLAST 162)
215 (UNSPEC_AESKEYGENASSIST 164)
223 (UNSPEC_VPERMIL2F128 168)
224 (UNSPEC_MASKLOAD 169)
225 (UNSPEC_MASKSTORE 170)
231 [(UNSPECV_BLOCKAGE 0)
232 (UNSPECV_STACK_PROBE 1)
244 (UNSPECV_PROLOGUE_USE 14)
246 (UNSPECV_VZEROALL 16)
247 (UNSPECV_VZEROUPPER 17)
250 ;; Constants to represent pcomtrue/pcomfalse variants
260 ;; Constants used in the SSE5 pperm instruction
262 [(PPERM_SRC 0x00) /* copy source */
263 (PPERM_INVERT 0x20) /* invert source */
264 (PPERM_REVERSE 0x40) /* bit reverse source */
265 (PPERM_REV_INV 0x60) /* bit reverse & invert src */
266 (PPERM_ZERO 0x80) /* all 0's */
267 (PPERM_ONES 0xa0) /* all 1's */
268 (PPERM_SIGN 0xc0) /* propagate sign bit */
269 (PPERM_INV_SIGN 0xe0) /* invert & propagate sign */
270 (PPERM_SRC1 0x00) /* use first source byte */
271 (PPERM_SRC2 0x10) /* use second source byte */
274 ;; Registers by name.
326 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
329 ;; In C guard expressions, put expressions which may be compile-time
330 ;; constants first. This allows for better optimization. For
331 ;; example, write "TARGET_64BIT && reload_completed", not
332 ;; "reload_completed && TARGET_64BIT".
336 (define_attr "cpu" "none,pentium,pentiumpro,geode,k6,athlon,k8,core2,atom,
338 (const (symbol_ref "ix86_schedule")))
340 ;; A basic instruction type. Refinements due to arguments to be
341 ;; provided in other attributes.
344 alu,alu1,negnot,imov,imovx,lea,
345 incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
346 icmp,test,ibr,setcc,icmov,
347 push,pop,call,callv,leave,
349 fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
350 sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
351 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,ssediv,sseins,
353 mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
354 (const_string "other"))
356 ;; Main data type used by the insn
358 "unknown,none,QI,HI,SI,DI,TI,OI,SF,DF,XF,TF,V8SF,V4DF,V4SF,V2DF,V2SF,V1DF"
359 (const_string "unknown"))
361 ;; The CPU unit operations uses.
362 (define_attr "unit" "integer,i387,sse,mmx,unknown"
363 (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
364 (const_string "i387")
365 (eq_attr "type" "sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
366 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,
367 ssecvt1,sseicvt,ssediv,sseins,ssemuladd,sse4arg")
369 (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
371 (eq_attr "type" "other")
372 (const_string "unknown")]
373 (const_string "integer")))
375 ;; The (bounding maximum) length of an instruction immediate.
376 (define_attr "length_immediate" ""
377 (cond [(eq_attr "type" "incdec,setcc,icmov,str,lea,other,multi,idiv,leave,
380 (eq_attr "unit" "i387,sse,mmx")
382 (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
384 (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
385 (eq_attr "type" "imov,test")
386 (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
387 (eq_attr "type" "call")
388 (if_then_else (match_operand 0 "constant_call_address_operand" "")
391 (eq_attr "type" "callv")
392 (if_then_else (match_operand 1 "constant_call_address_operand" "")
395 ;; We don't know the size before shorten_branches. Expect
396 ;; the instruction to fit for better scheduling.
397 (eq_attr "type" "ibr")
400 (symbol_ref "/* Update immediate_length and other attributes! */
401 gcc_unreachable (),1")))
403 ;; The (bounding maximum) length of an instruction address.
404 (define_attr "length_address" ""
405 (cond [(eq_attr "type" "str,other,multi,fxch")
407 (and (eq_attr "type" "call")
408 (match_operand 0 "constant_call_address_operand" ""))
410 (and (eq_attr "type" "callv")
411 (match_operand 1 "constant_call_address_operand" ""))
414 (symbol_ref "ix86_attr_length_address_default (insn)")))
416 ;; Set when length prefix is used.
417 (define_attr "prefix_data16" ""
418 (if_then_else (ior (eq_attr "mode" "HI")
419 (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
423 ;; Set when string REP prefix is used.
424 (define_attr "prefix_rep" ""
425 (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
429 ;; Set when 0f opcode prefix is used.
430 (define_attr "prefix_0f" ""
432 (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip")
433 (eq_attr "unit" "sse,mmx"))
437 ;; Set when REX opcode prefix is used.
438 (define_attr "prefix_rex" ""
439 (cond [(and (eq_attr "mode" "DI")
440 (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
442 (and (eq_attr "mode" "QI")
443 (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
446 (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
452 ;; There are also additional prefixes in SSSE3.
453 (define_attr "prefix_extra" "" (const_int 0))
455 ;; Prefix used: original, VEX or maybe VEX.
456 (define_attr "prefix" "orig,vex,maybe_vex"
457 (if_then_else (eq_attr "mode" "OI,V8SF,V4DF")
459 (const_string "orig")))
461 ;; There is a 8bit immediate for VEX.
462 (define_attr "prefix_vex_imm8" "" (const_int 0))
464 ;; VEX W bit is used.
465 (define_attr "prefix_vex_w" "" (const_int 0))
467 ;; The length of VEX prefix
468 (define_attr "length_vex" ""
469 (if_then_else (eq_attr "prefix_0f" "1")
470 (if_then_else (eq_attr "prefix_vex_w" "1")
471 (symbol_ref "ix86_attr_length_vex_default (insn, 1, 1)")
472 (symbol_ref "ix86_attr_length_vex_default (insn, 1, 0)"))
473 (if_then_else (eq_attr "prefix_vex_w" "1")
474 (symbol_ref "ix86_attr_length_vex_default (insn, 0, 1)")
475 (symbol_ref "ix86_attr_length_vex_default (insn, 0, 0)"))))
477 ;; Set when modrm byte is used.
478 (define_attr "modrm" ""
479 (cond [(eq_attr "type" "str,leave")
481 (eq_attr "unit" "i387")
483 (and (eq_attr "type" "incdec")
484 (ior (match_operand:SI 1 "register_operand" "")
485 (match_operand:HI 1 "register_operand" "")))
487 (and (eq_attr "type" "push")
488 (not (match_operand 1 "memory_operand" "")))
490 (and (eq_attr "type" "pop")
491 (not (match_operand 0 "memory_operand" "")))
493 (and (eq_attr "type" "imov")
494 (ior (and (match_operand 0 "register_operand" "")
495 (match_operand 1 "immediate_operand" ""))
496 (ior (and (match_operand 0 "ax_reg_operand" "")
497 (match_operand 1 "memory_displacement_only_operand" ""))
498 (and (match_operand 0 "memory_displacement_only_operand" "")
499 (match_operand 1 "ax_reg_operand" "")))))
501 (and (eq_attr "type" "call")
502 (match_operand 0 "constant_call_address_operand" ""))
504 (and (eq_attr "type" "callv")
505 (match_operand 1 "constant_call_address_operand" ""))
510 ;; The (bounding maximum) length of an instruction in bytes.
511 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
512 ;; Later we may want to split them and compute proper length as for
514 (define_attr "length" ""
515 (cond [(eq_attr "type" "other,multi,fistp,frndint")
517 (eq_attr "type" "fcmp")
519 (eq_attr "unit" "i387")
521 (plus (attr "prefix_data16")
522 (attr "length_address")))
523 (ior (eq_attr "prefix" "vex")
524 (and (eq_attr "prefix" "maybe_vex")
525 (ne (symbol_ref "TARGET_AVX") (const_int 0))))
526 (plus (attr "length_vex")
527 (plus (attr "prefix_vex_imm8")
529 (attr "length_address"))))]
530 (plus (plus (attr "modrm")
531 (plus (attr "prefix_0f")
532 (plus (attr "prefix_rex")
533 (plus (attr "prefix_extra")
535 (plus (attr "prefix_rep")
536 (plus (attr "prefix_data16")
537 (plus (attr "length_immediate")
538 (attr "length_address")))))))
540 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
541 ;; `store' if there is a simple memory reference therein, or `unknown'
542 ;; if the instruction is complex.
544 (define_attr "memory" "none,load,store,both,unknown"
545 (cond [(eq_attr "type" "other,multi,str")
546 (const_string "unknown")
547 (eq_attr "type" "lea,fcmov,fpspc")
548 (const_string "none")
549 (eq_attr "type" "fistp,leave")
550 (const_string "both")
551 (eq_attr "type" "frndint")
552 (const_string "load")
553 (eq_attr "type" "push")
554 (if_then_else (match_operand 1 "memory_operand" "")
555 (const_string "both")
556 (const_string "store"))
557 (eq_attr "type" "pop")
558 (if_then_else (match_operand 0 "memory_operand" "")
559 (const_string "both")
560 (const_string "load"))
561 (eq_attr "type" "setcc")
562 (if_then_else (match_operand 0 "memory_operand" "")
563 (const_string "store")
564 (const_string "none"))
565 (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
566 (if_then_else (ior (match_operand 0 "memory_operand" "")
567 (match_operand 1 "memory_operand" ""))
568 (const_string "load")
569 (const_string "none"))
570 (eq_attr "type" "ibr")
571 (if_then_else (match_operand 0 "memory_operand" "")
572 (const_string "load")
573 (const_string "none"))
574 (eq_attr "type" "call")
575 (if_then_else (match_operand 0 "constant_call_address_operand" "")
576 (const_string "none")
577 (const_string "load"))
578 (eq_attr "type" "callv")
579 (if_then_else (match_operand 1 "constant_call_address_operand" "")
580 (const_string "none")
581 (const_string "load"))
582 (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
583 (match_operand 1 "memory_operand" ""))
584 (const_string "both")
585 (and (match_operand 0 "memory_operand" "")
586 (match_operand 1 "memory_operand" ""))
587 (const_string "both")
588 (match_operand 0 "memory_operand" "")
589 (const_string "store")
590 (match_operand 1 "memory_operand" "")
591 (const_string "load")
593 "!alu1,negnot,ishift1,
594 imov,imovx,icmp,test,bitmanip,
596 sse,ssemov,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,sselog1,
597 sseiadd1,mmx,mmxmov,mmxcmp,mmxcvt")
598 (match_operand 2 "memory_operand" ""))
599 (const_string "load")
600 (and (eq_attr "type" "icmov,ssemuladd,sse4arg")
601 (match_operand 3 "memory_operand" ""))
602 (const_string "load")
604 (const_string "none")))
606 ;; Indicates if an instruction has both an immediate and a displacement.
608 (define_attr "imm_disp" "false,true,unknown"
609 (cond [(eq_attr "type" "other,multi")
610 (const_string "unknown")
611 (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
612 (and (match_operand 0 "memory_displacement_operand" "")
613 (match_operand 1 "immediate_operand" "")))
614 (const_string "true")
615 (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
616 (and (match_operand 0 "memory_displacement_operand" "")
617 (match_operand 2 "immediate_operand" "")))
618 (const_string "true")
620 (const_string "false")))
622 ;; Indicates if an FP operation has an integer source.
624 (define_attr "fp_int_src" "false,true"
625 (const_string "false"))
627 ;; Defines rounding mode of an FP operation.
629 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
630 (const_string "any"))
632 ;; Define attribute to classify add/sub insns that consumes carry flag (CF)
633 (define_attr "use_carry" "0,1" (const_string "0"))
635 ;; Define attribute to indicate unaligned ssemov insns
636 (define_attr "movu" "0,1" (const_string "0"))
638 ;; Describe a user's asm statement.
639 (define_asm_attributes
640 [(set_attr "length" "128")
641 (set_attr "type" "multi")])
643 ;; All integer comparison codes.
644 (define_code_iterator int_cond [ne eq ge gt le lt geu gtu leu ltu ])
646 ;; All floating-point comparison codes.
647 (define_code_iterator fp_cond [unordered ordered
648 uneq unge ungt unle unlt ltgt ])
650 (define_code_iterator plusminus [plus minus])
652 (define_code_iterator sat_plusminus [ss_plus us_plus ss_minus us_minus])
654 ;; Base name for define_insn
655 (define_code_attr plusminus_insn
656 [(plus "add") (ss_plus "ssadd") (us_plus "usadd")
657 (minus "sub") (ss_minus "sssub") (us_minus "ussub")])
659 ;; Base name for insn mnemonic.
660 (define_code_attr plusminus_mnemonic
661 [(plus "add") (ss_plus "adds") (us_plus "addus")
662 (minus "sub") (ss_minus "subs") (us_minus "subus")])
664 ;; Mark commutative operators as such in constraints.
665 (define_code_attr comm [(plus "%") (ss_plus "%") (us_plus "%")
666 (minus "") (ss_minus "") (us_minus "")])
668 ;; Mapping of signed max and min
669 (define_code_iterator smaxmin [smax smin])
671 ;; Mapping of unsigned max and min
672 (define_code_iterator umaxmin [umax umin])
674 ;; Mapping of signed/unsigned max and min
675 (define_code_iterator maxmin [smax smin umax umin])
677 ;; Base name for integer and FP insn mnemonic
678 (define_code_attr maxminiprefix [(smax "maxs") (smin "mins")
679 (umax "maxu") (umin "minu")])
680 (define_code_attr maxminfprefix [(smax "max") (smin "min")])
682 ;; Mapping of parallel logic operators
683 (define_code_iterator plogic [and ior xor])
685 ;; Base name for insn mnemonic.
686 (define_code_attr plogicprefix [(and "and") (ior "or") (xor "xor")])
688 ;; Mapping of abs neg operators
689 (define_code_iterator absneg [abs neg])
691 ;; Base name for x87 insn mnemonic.
692 (define_code_attr absnegprefix [(abs "abs") (neg "chs")])
694 ;; All single word integer modes.
695 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
697 ;; Single word integer modes without QImode.
698 (define_mode_iterator SWI248 [HI SI (DI "TARGET_64BIT")])
700 ;; Instruction suffix for integer modes.
701 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
703 ;; Register class for integer modes.
704 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
706 ;; Immediate operand constraint for integer modes.
707 (define_mode_attr i [(QI "n") (HI "n") (SI "i") (DI "e")])
709 ;; General operand predicate for integer modes.
710 (define_mode_attr general_operand
711 [(QI "general_operand")
712 (HI "general_operand")
713 (SI "general_operand")
714 (DI "x86_64_general_operand")])
716 ;; SSE and x87 SFmode and DFmode floating point modes
717 (define_mode_iterator MODEF [SF DF])
719 ;; All x87 floating point modes
720 (define_mode_iterator X87MODEF [SF DF XF])
722 ;; All integer modes handled by x87 fisttp operator.
723 (define_mode_iterator X87MODEI [HI SI DI])
725 ;; All integer modes handled by integer x87 operators.
726 (define_mode_iterator X87MODEI12 [HI SI])
728 ;; All integer modes handled by SSE cvtts?2si* operators.
729 (define_mode_iterator SSEMODEI24 [SI DI])
731 ;; SSE asm suffix for floating point modes
732 (define_mode_attr ssemodefsuffix [(SF "s") (DF "d")])
734 ;; SSE vector mode corresponding to a scalar mode
735 (define_mode_attr ssevecmode
736 [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
738 ;; Instruction suffix for REX 64bit operators.
739 (define_mode_attr rex64suffix [(SI "") (DI "{q}")])
741 ;; This mode iterator allows :P to be used for patterns that operate on
742 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
743 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
746 ;; Scheduling descriptions
748 (include "pentium.md")
751 (include "athlon.md")
756 ;; Operand and operator predicates and constraints
758 (include "predicates.md")
759 (include "constraints.md")
762 ;; Compare and branch/compare and store instructions.
764 (define_expand "cbranchti4"
765 [(set (reg:CC FLAGS_REG)
766 (compare:CC (match_operand:TI 1 "nonimmediate_operand" "")
767 (match_operand:TI 2 "x86_64_general_operand" "")))
768 (set (pc) (if_then_else
769 (match_operator 0 "comparison_operator"
772 (label_ref (match_operand 3 "" ""))
776 if (MEM_P (operands[1]) && MEM_P (operands[2]))
777 operands[1] = force_reg (TImode, operands[1]);
778 ix86_compare_op0 = operands[1];
779 ix86_compare_op1 = operands[2];
780 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
784 (define_expand "cbranchdi4"
785 [(set (reg:CC FLAGS_REG)
786 (compare:CC (match_operand:DI 1 "nonimmediate_operand" "")
787 (match_operand:DI 2 "x86_64_general_operand" "")))
788 (set (pc) (if_then_else
789 (match_operator 0 "comparison_operator"
792 (label_ref (match_operand 3 "" ""))
796 if (MEM_P (operands[1]) && MEM_P (operands[2]))
797 operands[1] = force_reg (DImode, operands[1]);
798 ix86_compare_op0 = operands[1];
799 ix86_compare_op1 = operands[2];
800 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
804 (define_expand "cstoredi4"
805 [(set (reg:CC FLAGS_REG)
806 (compare:CC (match_operand:DI 2 "nonimmediate_operand" "")
807 (match_operand:DI 3 "x86_64_general_operand" "")))
808 (set (match_operand:QI 0 "register_operand" "")
809 (match_operator 1 "comparison_operator"
814 if (MEM_P (operands[2]) && MEM_P (operands[3]))
815 operands[2] = force_reg (DImode, operands[2]);
816 ix86_compare_op0 = operands[2];
817 ix86_compare_op1 = operands[3];
818 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
822 (define_expand "cbranchsi4"
823 [(set (reg:CC FLAGS_REG)
824 (compare:CC (match_operand:SI 1 "cmpsi_operand" "")
825 (match_operand:SI 2 "general_operand" "")))
826 (set (pc) (if_then_else
827 (match_operator 0 "comparison_operator"
830 (label_ref (match_operand 3 "" ""))
834 if (MEM_P (operands[1]) && MEM_P (operands[2]))
835 operands[1] = force_reg (SImode, operands[1]);
836 ix86_compare_op0 = operands[1];
837 ix86_compare_op1 = operands[2];
838 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
842 (define_expand "cstoresi4"
843 [(set (reg:CC FLAGS_REG)
844 (compare:CC (match_operand:SI 2 "cmpsi_operand" "")
845 (match_operand:SI 3 "general_operand" "")))
846 (set (match_operand:QI 0 "register_operand" "")
847 (match_operator 1 "comparison_operator"
852 if (MEM_P (operands[2]) && MEM_P (operands[3]))
853 operands[2] = force_reg (SImode, operands[2]);
854 ix86_compare_op0 = operands[2];
855 ix86_compare_op1 = operands[3];
856 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
860 (define_expand "cbranchhi4"
861 [(set (reg:CC FLAGS_REG)
862 (compare:CC (match_operand:HI 1 "nonimmediate_operand" "")
863 (match_operand:HI 2 "general_operand" "")))
864 (set (pc) (if_then_else
865 (match_operator 0 "comparison_operator"
868 (label_ref (match_operand 3 "" ""))
872 if (MEM_P (operands[1]) && MEM_P (operands[2]))
873 operands[1] = force_reg (HImode, operands[1]);
874 ix86_compare_op0 = operands[1];
875 ix86_compare_op1 = operands[2];
876 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
880 (define_expand "cstorehi4"
881 [(set (reg:CC FLAGS_REG)
882 (compare:CC (match_operand:HI 2 "nonimmediate_operand" "")
883 (match_operand:HI 3 "general_operand" "")))
884 (set (match_operand:QI 0 "register_operand" "")
885 (match_operator 1 "comparison_operator"
890 if (MEM_P (operands[2]) && MEM_P (operands[3]))
891 operands[2] = force_reg (HImode, operands[2]);
892 ix86_compare_op0 = operands[2];
893 ix86_compare_op1 = operands[3];
894 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
899 (define_expand "cbranchqi4"
900 [(set (reg:CC FLAGS_REG)
901 (compare:CC (match_operand:QI 1 "nonimmediate_operand" "")
902 (match_operand:QI 2 "general_operand" "")))
903 (set (pc) (if_then_else
904 (match_operator 0 "comparison_operator"
907 (label_ref (match_operand 3 "" ""))
911 if (MEM_P (operands[1]) && MEM_P (operands[2]))
912 operands[1] = force_reg (QImode, operands[1]);
913 ix86_compare_op0 = operands[1];
914 ix86_compare_op1 = operands[2];
915 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
920 (define_expand "cstoreqi4"
921 [(set (reg:CC FLAGS_REG)
922 (compare:CC (match_operand:QI 2 "nonimmediate_operand" "")
923 (match_operand:QI 3 "general_operand" "")))
924 (set (match_operand:QI 0 "register_operand" "")
925 (match_operator 1 "comparison_operator"
930 if (MEM_P (operands[2]) && MEM_P (operands[3]))
931 operands[2] = force_reg (QImode, operands[2]);
932 ix86_compare_op0 = operands[2];
933 ix86_compare_op1 = operands[3];
934 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
939 (define_insn "cmpdi_ccno_1_rex64"
940 [(set (reg FLAGS_REG)
941 (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
942 (match_operand:DI 1 "const0_operand" "")))]
943 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
946 cmp{q}\t{%1, %0|%0, %1}"
947 [(set_attr "type" "test,icmp")
948 (set_attr "length_immediate" "0,1")
949 (set_attr "mode" "DI")])
951 (define_insn "*cmpdi_minus_1_rex64"
952 [(set (reg FLAGS_REG)
953 (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
954 (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
956 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
957 "cmp{q}\t{%1, %0|%0, %1}"
958 [(set_attr "type" "icmp")
959 (set_attr "mode" "DI")])
961 (define_expand "cmpdi_1_rex64"
962 [(set (reg:CC FLAGS_REG)
963 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
964 (match_operand:DI 1 "general_operand" "")))]
968 (define_insn "cmpdi_1_insn_rex64"
969 [(set (reg FLAGS_REG)
970 (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
971 (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
972 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
973 "cmp{q}\t{%1, %0|%0, %1}"
974 [(set_attr "type" "icmp")
975 (set_attr "mode" "DI")])
978 (define_insn "*cmpsi_ccno_1"
979 [(set (reg FLAGS_REG)
980 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
981 (match_operand:SI 1 "const0_operand" "")))]
982 "ix86_match_ccmode (insn, CCNOmode)"
985 cmp{l}\t{%1, %0|%0, %1}"
986 [(set_attr "type" "test,icmp")
987 (set_attr "length_immediate" "0,1")
988 (set_attr "mode" "SI")])
990 (define_insn "*cmpsi_minus_1"
991 [(set (reg FLAGS_REG)
992 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
993 (match_operand:SI 1 "general_operand" "ri,mr"))
995 "ix86_match_ccmode (insn, CCGOCmode)"
996 "cmp{l}\t{%1, %0|%0, %1}"
997 [(set_attr "type" "icmp")
998 (set_attr "mode" "SI")])
1000 (define_expand "cmpsi_1"
1001 [(set (reg:CC FLAGS_REG)
1002 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "")
1003 (match_operand:SI 1 "general_operand" "")))]
1007 (define_insn "*cmpsi_1_insn"
1008 [(set (reg FLAGS_REG)
1009 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
1010 (match_operand:SI 1 "general_operand" "ri,mr")))]
1011 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
1012 && ix86_match_ccmode (insn, CCmode)"
1013 "cmp{l}\t{%1, %0|%0, %1}"
1014 [(set_attr "type" "icmp")
1015 (set_attr "mode" "SI")])
1017 (define_insn "*cmphi_ccno_1"
1018 [(set (reg FLAGS_REG)
1019 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
1020 (match_operand:HI 1 "const0_operand" "")))]
1021 "ix86_match_ccmode (insn, CCNOmode)"
1024 cmp{w}\t{%1, %0|%0, %1}"
1025 [(set_attr "type" "test,icmp")
1026 (set_attr "length_immediate" "0,1")
1027 (set_attr "mode" "HI")])
1029 (define_insn "*cmphi_minus_1"
1030 [(set (reg FLAGS_REG)
1031 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
1032 (match_operand:HI 1 "general_operand" "rn,mr"))
1034 "ix86_match_ccmode (insn, CCGOCmode)"
1035 "cmp{w}\t{%1, %0|%0, %1}"
1036 [(set_attr "type" "icmp")
1037 (set_attr "mode" "HI")])
1039 (define_insn "*cmphi_1"
1040 [(set (reg FLAGS_REG)
1041 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
1042 (match_operand:HI 1 "general_operand" "rn,mr")))]
1043 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
1044 && ix86_match_ccmode (insn, CCmode)"
1045 "cmp{w}\t{%1, %0|%0, %1}"
1046 [(set_attr "type" "icmp")
1047 (set_attr "mode" "HI")])
1049 (define_insn "*cmpqi_ccno_1"
1050 [(set (reg FLAGS_REG)
1051 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
1052 (match_operand:QI 1 "const0_operand" "")))]
1053 "ix86_match_ccmode (insn, CCNOmode)"
1056 cmp{b}\t{$0, %0|%0, 0}"
1057 [(set_attr "type" "test,icmp")
1058 (set_attr "length_immediate" "0,1")
1059 (set_attr "mode" "QI")])
1061 (define_insn "*cmpqi_1"
1062 [(set (reg FLAGS_REG)
1063 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
1064 (match_operand:QI 1 "general_operand" "qn,mq")))]
1065 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
1066 && ix86_match_ccmode (insn, CCmode)"
1067 "cmp{b}\t{%1, %0|%0, %1}"
1068 [(set_attr "type" "icmp")
1069 (set_attr "mode" "QI")])
1071 (define_insn "*cmpqi_minus_1"
1072 [(set (reg FLAGS_REG)
1073 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
1074 (match_operand:QI 1 "general_operand" "qn,mq"))
1076 "ix86_match_ccmode (insn, CCGOCmode)"
1077 "cmp{b}\t{%1, %0|%0, %1}"
1078 [(set_attr "type" "icmp")
1079 (set_attr "mode" "QI")])
1081 (define_insn "*cmpqi_ext_1"
1082 [(set (reg FLAGS_REG)
1084 (match_operand:QI 0 "general_operand" "Qm")
1087 (match_operand 1 "ext_register_operand" "Q")
1089 (const_int 8)) 0)))]
1090 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1091 "cmp{b}\t{%h1, %0|%0, %h1}"
1092 [(set_attr "type" "icmp")
1093 (set_attr "mode" "QI")])
1095 (define_insn "*cmpqi_ext_1_rex64"
1096 [(set (reg FLAGS_REG)
1098 (match_operand:QI 0 "register_operand" "Q")
1101 (match_operand 1 "ext_register_operand" "Q")
1103 (const_int 8)) 0)))]
1104 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1105 "cmp{b}\t{%h1, %0|%0, %h1}"
1106 [(set_attr "type" "icmp")
1107 (set_attr "mode" "QI")])
1109 (define_insn "*cmpqi_ext_2"
1110 [(set (reg FLAGS_REG)
1114 (match_operand 0 "ext_register_operand" "Q")
1117 (match_operand:QI 1 "const0_operand" "")))]
1118 "ix86_match_ccmode (insn, CCNOmode)"
1120 [(set_attr "type" "test")
1121 (set_attr "length_immediate" "0")
1122 (set_attr "mode" "QI")])
1124 (define_expand "cmpqi_ext_3"
1125 [(set (reg:CC FLAGS_REG)
1129 (match_operand 0 "ext_register_operand" "")
1132 (match_operand:QI 1 "general_operand" "")))]
1136 (define_insn "cmpqi_ext_3_insn"
1137 [(set (reg FLAGS_REG)
1141 (match_operand 0 "ext_register_operand" "Q")
1144 (match_operand:QI 1 "general_operand" "Qmn")))]
1145 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1146 "cmp{b}\t{%1, %h0|%h0, %1}"
1147 [(set_attr "type" "icmp")
1148 (set_attr "mode" "QI")])
1150 (define_insn "cmpqi_ext_3_insn_rex64"
1151 [(set (reg FLAGS_REG)
1155 (match_operand 0 "ext_register_operand" "Q")
1158 (match_operand:QI 1 "nonmemory_operand" "Qn")))]
1159 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1160 "cmp{b}\t{%1, %h0|%h0, %1}"
1161 [(set_attr "type" "icmp")
1162 (set_attr "mode" "QI")])
1164 (define_insn "*cmpqi_ext_4"
1165 [(set (reg FLAGS_REG)
1169 (match_operand 0 "ext_register_operand" "Q")
1174 (match_operand 1 "ext_register_operand" "Q")
1176 (const_int 8)) 0)))]
1177 "ix86_match_ccmode (insn, CCmode)"
1178 "cmp{b}\t{%h1, %h0|%h0, %h1}"
1179 [(set_attr "type" "icmp")
1180 (set_attr "mode" "QI")])
1182 ;; These implement float point compares.
1183 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
1184 ;; which would allow mix and match FP modes on the compares. Which is what
1185 ;; the old patterns did, but with many more of them.
1187 (define_expand "cbranchxf4"
1188 [(set (reg:CC FLAGS_REG)
1189 (compare:CC (match_operand:XF 1 "nonmemory_operand" "")
1190 (match_operand:XF 2 "nonmemory_operand" "")))
1191 (set (pc) (if_then_else
1192 (match_operator 0 "comparison_operator"
1195 (label_ref (match_operand 3 "" ""))
1199 ix86_compare_op0 = operands[1];
1200 ix86_compare_op1 = operands[2];
1201 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
1205 (define_expand "cstorexf4"
1206 [(set (reg:CC FLAGS_REG)
1207 (compare:CC (match_operand:XF 2 "nonmemory_operand" "")
1208 (match_operand:XF 3 "nonmemory_operand" "")))
1209 (set (match_operand:QI 0 "register_operand" "")
1210 (match_operator 1 "comparison_operator"
1215 ix86_compare_op0 = operands[2];
1216 ix86_compare_op1 = operands[3];
1217 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
1221 (define_expand "cbranch<mode>4"
1222 [(set (reg:CC FLAGS_REG)
1223 (compare:CC (match_operand:MODEF 1 "cmp_fp_expander_operand" "")
1224 (match_operand:MODEF 2 "cmp_fp_expander_operand" "")))
1225 (set (pc) (if_then_else
1226 (match_operator 0 "comparison_operator"
1229 (label_ref (match_operand 3 "" ""))
1231 "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1233 ix86_compare_op0 = operands[1];
1234 ix86_compare_op1 = operands[2];
1235 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
1239 (define_expand "cstore<mode>4"
1240 [(set (reg:CC FLAGS_REG)
1241 (compare:CC (match_operand:MODEF 2 "cmp_fp_expander_operand" "")
1242 (match_operand:MODEF 3 "cmp_fp_expander_operand" "")))
1243 (set (match_operand:QI 0 "register_operand" "")
1244 (match_operator 1 "comparison_operator"
1247 "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1249 ix86_compare_op0 = operands[2];
1250 ix86_compare_op1 = operands[3];
1251 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
1255 (define_expand "cbranchcc4"
1256 [(set (pc) (if_then_else
1257 (match_operator 0 "comparison_operator"
1258 [(match_operand 1 "flags_reg_operand" "")
1259 (match_operand 2 "const0_operand" "")])
1260 (label_ref (match_operand 3 "" ""))
1264 ix86_compare_op0 = operands[1];
1265 ix86_compare_op1 = operands[2];
1266 ix86_expand_branch (GET_CODE (operands[0]), operands[3]);
1270 (define_expand "cstorecc4"
1271 [(set (match_operand:QI 0 "register_operand" "")
1272 (match_operator 1 "comparison_operator"
1273 [(match_operand 2 "flags_reg_operand" "")
1274 (match_operand 3 "const0_operand" "")]))]
1277 ix86_compare_op0 = operands[2];
1278 ix86_compare_op1 = operands[3];
1279 ix86_expand_setcc (GET_CODE (operands[1]), operands[0]);
1284 ;; FP compares, step 1:
1285 ;; Set the FP condition codes.
1287 ;; CCFPmode compare with exceptions
1288 ;; CCFPUmode compare with no exceptions
1290 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1291 ;; used to manage the reg stack popping would not be preserved.
1293 (define_insn "*cmpfp_0"
1294 [(set (match_operand:HI 0 "register_operand" "=a")
1297 (match_operand 1 "register_operand" "f")
1298 (match_operand 2 "const0_operand" ""))]
1300 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1301 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1302 "* return output_fp_compare (insn, operands, 0, 0);"
1303 [(set_attr "type" "multi")
1304 (set_attr "unit" "i387")
1306 (cond [(match_operand:SF 1 "" "")
1308 (match_operand:DF 1 "" "")
1311 (const_string "XF")))])
1313 (define_insn_and_split "*cmpfp_0_cc"
1314 [(set (reg:CCFP FLAGS_REG)
1316 (match_operand 1 "register_operand" "f")
1317 (match_operand 2 "const0_operand" "")))
1318 (clobber (match_operand:HI 0 "register_operand" "=a"))]
1319 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1320 && TARGET_SAHF && !TARGET_CMOVE
1321 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1323 "&& reload_completed"
1326 [(compare:CCFP (match_dup 1)(match_dup 2))]
1328 (set (reg:CC FLAGS_REG)
1329 (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1331 [(set_attr "type" "multi")
1332 (set_attr "unit" "i387")
1334 (cond [(match_operand:SF 1 "" "")
1336 (match_operand:DF 1 "" "")
1339 (const_string "XF")))])
1341 (define_insn "*cmpfp_xf"
1342 [(set (match_operand:HI 0 "register_operand" "=a")
1345 (match_operand:XF 1 "register_operand" "f")
1346 (match_operand:XF 2 "register_operand" "f"))]
1349 "* return output_fp_compare (insn, operands, 0, 0);"
1350 [(set_attr "type" "multi")
1351 (set_attr "unit" "i387")
1352 (set_attr "mode" "XF")])
1354 (define_insn_and_split "*cmpfp_xf_cc"
1355 [(set (reg:CCFP FLAGS_REG)
1357 (match_operand:XF 1 "register_operand" "f")
1358 (match_operand:XF 2 "register_operand" "f")))
1359 (clobber (match_operand:HI 0 "register_operand" "=a"))]
1361 && TARGET_SAHF && !TARGET_CMOVE"
1363 "&& reload_completed"
1366 [(compare:CCFP (match_dup 1)(match_dup 2))]
1368 (set (reg:CC FLAGS_REG)
1369 (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1371 [(set_attr "type" "multi")
1372 (set_attr "unit" "i387")
1373 (set_attr "mode" "XF")])
1375 (define_insn "*cmpfp_<mode>"
1376 [(set (match_operand:HI 0 "register_operand" "=a")
1379 (match_operand:MODEF 1 "register_operand" "f")
1380 (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1383 "* return output_fp_compare (insn, operands, 0, 0);"
1384 [(set_attr "type" "multi")
1385 (set_attr "unit" "i387")
1386 (set_attr "mode" "<MODE>")])
1388 (define_insn_and_split "*cmpfp_<mode>_cc"
1389 [(set (reg:CCFP FLAGS_REG)
1391 (match_operand:MODEF 1 "register_operand" "f")
1392 (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1393 (clobber (match_operand:HI 0 "register_operand" "=a"))]
1395 && TARGET_SAHF && !TARGET_CMOVE"
1397 "&& reload_completed"
1400 [(compare:CCFP (match_dup 1)(match_dup 2))]
1402 (set (reg:CC FLAGS_REG)
1403 (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1405 [(set_attr "type" "multi")
1406 (set_attr "unit" "i387")
1407 (set_attr "mode" "<MODE>")])
1409 (define_insn "*cmpfp_u"
1410 [(set (match_operand:HI 0 "register_operand" "=a")
1413 (match_operand 1 "register_operand" "f")
1414 (match_operand 2 "register_operand" "f"))]
1416 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1417 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1418 "* return output_fp_compare (insn, operands, 0, 1);"
1419 [(set_attr "type" "multi")
1420 (set_attr "unit" "i387")
1422 (cond [(match_operand:SF 1 "" "")
1424 (match_operand:DF 1 "" "")
1427 (const_string "XF")))])
1429 (define_insn_and_split "*cmpfp_u_cc"
1430 [(set (reg:CCFPU FLAGS_REG)
1432 (match_operand 1 "register_operand" "f")
1433 (match_operand 2 "register_operand" "f")))
1434 (clobber (match_operand:HI 0 "register_operand" "=a"))]
1435 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1436 && TARGET_SAHF && !TARGET_CMOVE
1437 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1439 "&& reload_completed"
1442 [(compare:CCFPU (match_dup 1)(match_dup 2))]
1444 (set (reg:CC FLAGS_REG)
1445 (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1447 [(set_attr "type" "multi")
1448 (set_attr "unit" "i387")
1450 (cond [(match_operand:SF 1 "" "")
1452 (match_operand:DF 1 "" "")
1455 (const_string "XF")))])
1457 (define_insn "*cmpfp_<mode>"
1458 [(set (match_operand:HI 0 "register_operand" "=a")
1461 (match_operand 1 "register_operand" "f")
1462 (match_operator 3 "float_operator"
1463 [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
1465 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1466 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1467 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1468 "* return output_fp_compare (insn, operands, 0, 0);"
1469 [(set_attr "type" "multi")
1470 (set_attr "unit" "i387")
1471 (set_attr "fp_int_src" "true")
1472 (set_attr "mode" "<MODE>")])
1474 (define_insn_and_split "*cmpfp_<mode>_cc"
1475 [(set (reg:CCFP FLAGS_REG)
1477 (match_operand 1 "register_operand" "f")
1478 (match_operator 3 "float_operator"
1479 [(match_operand:X87MODEI12 2 "memory_operand" "m")])))
1480 (clobber (match_operand:HI 0 "register_operand" "=a"))]
1481 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1482 && TARGET_SAHF && !TARGET_CMOVE
1483 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1484 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1486 "&& reload_completed"
1491 (match_op_dup 3 [(match_dup 2)]))]
1493 (set (reg:CC FLAGS_REG)
1494 (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1496 [(set_attr "type" "multi")
1497 (set_attr "unit" "i387")
1498 (set_attr "fp_int_src" "true")
1499 (set_attr "mode" "<MODE>")])
1501 ;; FP compares, step 2
1502 ;; Move the fpsw to ax.
1504 (define_insn "x86_fnstsw_1"
1505 [(set (match_operand:HI 0 "register_operand" "=a")
1506 (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1509 [(set_attr "length" "2")
1510 (set_attr "mode" "SI")
1511 (set_attr "unit" "i387")])
1513 ;; FP compares, step 3
1514 ;; Get ax into flags, general case.
1516 (define_insn "x86_sahf_1"
1517 [(set (reg:CC FLAGS_REG)
1518 (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1522 #ifdef HAVE_AS_IX86_SAHF
1525 return ".byte\t0x9e";
1528 [(set_attr "length" "1")
1529 (set_attr "athlon_decode" "vector")
1530 (set_attr "amdfam10_decode" "direct")
1531 (set_attr "mode" "SI")])
1533 ;; Pentium Pro can do steps 1 through 3 in one go.
1534 ;; comi*, ucomi*, fcomi*, ficomi*,fucomi* (i387 instructions set condition codes)
1535 (define_insn "*cmpfp_i_mixed"
1536 [(set (reg:CCFP FLAGS_REG)
1537 (compare:CCFP (match_operand 0 "register_operand" "f,x")
1538 (match_operand 1 "nonimmediate_operand" "f,xm")))]
1539 "TARGET_MIX_SSE_I387
1540 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1541 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1542 "* return output_fp_compare (insn, operands, 1, 0);"
1543 [(set_attr "type" "fcmp,ssecomi")
1544 (set_attr "prefix" "orig,maybe_vex")
1546 (if_then_else (match_operand:SF 1 "" "")
1548 (const_string "DF")))
1549 (set_attr "athlon_decode" "vector")
1550 (set_attr "amdfam10_decode" "direct")])
1552 (define_insn "*cmpfp_i_sse"
1553 [(set (reg:CCFP FLAGS_REG)
1554 (compare:CCFP (match_operand 0 "register_operand" "x")
1555 (match_operand 1 "nonimmediate_operand" "xm")))]
1557 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1558 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1559 "* return output_fp_compare (insn, operands, 1, 0);"
1560 [(set_attr "type" "ssecomi")
1561 (set_attr "prefix" "maybe_vex")
1563 (if_then_else (match_operand:SF 1 "" "")
1565 (const_string "DF")))
1566 (set_attr "athlon_decode" "vector")
1567 (set_attr "amdfam10_decode" "direct")])
1569 (define_insn "*cmpfp_i_i387"
1570 [(set (reg:CCFP FLAGS_REG)
1571 (compare:CCFP (match_operand 0 "register_operand" "f")
1572 (match_operand 1 "register_operand" "f")))]
1573 "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1575 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1576 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1577 "* return output_fp_compare (insn, operands, 1, 0);"
1578 [(set_attr "type" "fcmp")
1580 (cond [(match_operand:SF 1 "" "")
1582 (match_operand:DF 1 "" "")
1585 (const_string "XF")))
1586 (set_attr "athlon_decode" "vector")
1587 (set_attr "amdfam10_decode" "direct")])
1589 (define_insn "*cmpfp_iu_mixed"
1590 [(set (reg:CCFPU FLAGS_REG)
1591 (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1592 (match_operand 1 "nonimmediate_operand" "f,xm")))]
1593 "TARGET_MIX_SSE_I387
1594 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1595 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1596 "* return output_fp_compare (insn, operands, 1, 1);"
1597 [(set_attr "type" "fcmp,ssecomi")
1598 (set_attr "prefix" "orig,maybe_vex")
1600 (if_then_else (match_operand:SF 1 "" "")
1602 (const_string "DF")))
1603 (set_attr "athlon_decode" "vector")
1604 (set_attr "amdfam10_decode" "direct")])
1606 (define_insn "*cmpfp_iu_sse"
1607 [(set (reg:CCFPU FLAGS_REG)
1608 (compare:CCFPU (match_operand 0 "register_operand" "x")
1609 (match_operand 1 "nonimmediate_operand" "xm")))]
1611 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1612 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1613 "* return output_fp_compare (insn, operands, 1, 1);"
1614 [(set_attr "type" "ssecomi")
1615 (set_attr "prefix" "maybe_vex")
1617 (if_then_else (match_operand:SF 1 "" "")
1619 (const_string "DF")))
1620 (set_attr "athlon_decode" "vector")
1621 (set_attr "amdfam10_decode" "direct")])
1623 (define_insn "*cmpfp_iu_387"
1624 [(set (reg:CCFPU FLAGS_REG)
1625 (compare:CCFPU (match_operand 0 "register_operand" "f")
1626 (match_operand 1 "register_operand" "f")))]
1627 "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1629 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1630 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1631 "* return output_fp_compare (insn, operands, 1, 1);"
1632 [(set_attr "type" "fcmp")
1634 (cond [(match_operand:SF 1 "" "")
1636 (match_operand:DF 1 "" "")
1639 (const_string "XF")))
1640 (set_attr "athlon_decode" "vector")
1641 (set_attr "amdfam10_decode" "direct")])
1643 ;; Move instructions.
1645 ;; General case of fullword move.
1647 (define_expand "movsi"
1648 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1649 (match_operand:SI 1 "general_operand" ""))]
1651 "ix86_expand_move (SImode, operands); DONE;")
1653 ;; Push/pop instructions. They are separate since autoinc/dec is not a
1656 ;; %%% We don't use a post-inc memory reference because x86 is not a
1657 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1658 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1659 ;; targets without our curiosities, and it is just as easy to represent
1660 ;; this differently.
1662 (define_insn "*pushsi2"
1663 [(set (match_operand:SI 0 "push_operand" "=<")
1664 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1667 [(set_attr "type" "push")
1668 (set_attr "mode" "SI")])
1670 ;; For 64BIT abi we always round up to 8 bytes.
1671 (define_insn "*pushsi2_rex64"
1672 [(set (match_operand:SI 0 "push_operand" "=X")
1673 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1676 [(set_attr "type" "push")
1677 (set_attr "mode" "SI")])
1679 (define_insn "*pushsi2_prologue"
1680 [(set (match_operand:SI 0 "push_operand" "=<")
1681 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1682 (clobber (mem:BLK (scratch)))]
1685 [(set_attr "type" "push")
1686 (set_attr "mode" "SI")])
1688 (define_insn "*popsi1_epilogue"
1689 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1690 (mem:SI (reg:SI SP_REG)))
1691 (set (reg:SI SP_REG)
1692 (plus:SI (reg:SI SP_REG) (const_int 4)))
1693 (clobber (mem:BLK (scratch)))]
1696 [(set_attr "type" "pop")
1697 (set_attr "mode" "SI")])
1699 (define_insn "popsi1"
1700 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1701 (mem:SI (reg:SI SP_REG)))
1702 (set (reg:SI SP_REG)
1703 (plus:SI (reg:SI SP_REG) (const_int 4)))]
1706 [(set_attr "type" "pop")
1707 (set_attr "mode" "SI")])
1709 (define_insn "*movsi_xor"
1710 [(set (match_operand:SI 0 "register_operand" "=r")
1711 (match_operand:SI 1 "const0_operand" ""))
1712 (clobber (reg:CC FLAGS_REG))]
1715 [(set_attr "type" "alu1")
1716 (set_attr "mode" "SI")
1717 (set_attr "length_immediate" "0")])
1719 (define_insn "*movsi_or"
1720 [(set (match_operand:SI 0 "register_operand" "=r")
1721 (match_operand:SI 1 "immediate_operand" "i"))
1722 (clobber (reg:CC FLAGS_REG))]
1724 && operands[1] == constm1_rtx"
1726 operands[1] = constm1_rtx;
1727 return "or{l}\t{%1, %0|%0, %1}";
1729 [(set_attr "type" "alu1")
1730 (set_attr "mode" "SI")
1731 (set_attr "length_immediate" "1")])
1733 (define_insn "*movsi_1"
1734 [(set (match_operand:SI 0 "nonimmediate_operand"
1735 "=r,m ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
1736 (match_operand:SI 1 "general_operand"
1737 "g ,ri,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r ,m "))]
1738 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1740 switch (get_attr_type (insn))
1743 if (get_attr_mode (insn) == MODE_TI)
1744 return "%vpxor\t%0, %d0";
1745 return "%vxorps\t%0, %d0";
1748 switch (get_attr_mode (insn))
1751 return "%vmovdqa\t{%1, %0|%0, %1}";
1753 return "%vmovaps\t{%1, %0|%0, %1}";
1755 return "%vmovd\t{%1, %0|%0, %1}";
1757 return "%vmovss\t{%1, %0|%0, %1}";
1763 return "pxor\t%0, %0";
1766 if (get_attr_mode (insn) == MODE_DI)
1767 return "movq\t{%1, %0|%0, %1}";
1768 return "movd\t{%1, %0|%0, %1}";
1771 return "lea{l}\t{%1, %0|%0, %1}";
1774 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1775 return "mov{l}\t{%1, %0|%0, %1}";
1779 (cond [(eq_attr "alternative" "2")
1780 (const_string "mmx")
1781 (eq_attr "alternative" "3,4,5")
1782 (const_string "mmxmov")
1783 (eq_attr "alternative" "6")
1784 (const_string "sselog1")
1785 (eq_attr "alternative" "7,8,9,10,11")
1786 (const_string "ssemov")
1787 (match_operand:DI 1 "pic_32bit_operand" "")
1788 (const_string "lea")
1790 (const_string "imov")))
1791 (set (attr "prefix")
1792 (if_then_else (eq_attr "alternative" "0,1,2,3,4,5")
1793 (const_string "orig")
1794 (const_string "maybe_vex")))
1796 (cond [(eq_attr "alternative" "2,3")
1798 (eq_attr "alternative" "6,7")
1800 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1801 (const_string "V4SF")
1802 (const_string "TI"))
1803 (and (eq_attr "alternative" "8,9,10,11")
1804 (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1807 (const_string "SI")))])
1809 ;; Stores and loads of ax to arbitrary constant address.
1810 ;; We fake an second form of instruction to force reload to load address
1811 ;; into register when rax is not available
1812 (define_insn "*movabssi_1_rex64"
1813 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1814 (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1815 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1817 movabs{l}\t{%1, %P0|%P0, %1}
1818 mov{l}\t{%1, %a0|%a0, %1}"
1819 [(set_attr "type" "imov")
1820 (set_attr "modrm" "0,*")
1821 (set_attr "length_address" "8,0")
1822 (set_attr "length_immediate" "0,*")
1823 (set_attr "memory" "store")
1824 (set_attr "mode" "SI")])
1826 (define_insn "*movabssi_2_rex64"
1827 [(set (match_operand:SI 0 "register_operand" "=a,r")
1828 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1829 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1831 movabs{l}\t{%P1, %0|%0, %P1}
1832 mov{l}\t{%a1, %0|%0, %a1}"
1833 [(set_attr "type" "imov")
1834 (set_attr "modrm" "0,*")
1835 (set_attr "length_address" "8,0")
1836 (set_attr "length_immediate" "0")
1837 (set_attr "memory" "load")
1838 (set_attr "mode" "SI")])
1840 (define_insn "*swapsi"
1841 [(set (match_operand:SI 0 "register_operand" "+r")
1842 (match_operand:SI 1 "register_operand" "+r"))
1847 [(set_attr "type" "imov")
1848 (set_attr "mode" "SI")
1849 (set_attr "pent_pair" "np")
1850 (set_attr "athlon_decode" "vector")
1851 (set_attr "amdfam10_decode" "double")])
1853 (define_expand "movhi"
1854 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1855 (match_operand:HI 1 "general_operand" ""))]
1857 "ix86_expand_move (HImode, operands); DONE;")
1859 (define_insn "*pushhi2"
1860 [(set (match_operand:HI 0 "push_operand" "=X")
1861 (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))]
1864 [(set_attr "type" "push")
1865 (set_attr "mode" "SI")])
1867 ;; For 64BIT abi we always round up to 8 bytes.
1868 (define_insn "*pushhi2_rex64"
1869 [(set (match_operand:HI 0 "push_operand" "=X")
1870 (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))]
1873 [(set_attr "type" "push")
1874 (set_attr "mode" "DI")])
1876 (define_insn "*movhi_1"
1877 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1878 (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1879 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1881 switch (get_attr_type (insn))
1884 /* movzwl is faster than movw on p2 due to partial word stalls,
1885 though not as fast as an aligned movl. */
1886 return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1888 if (get_attr_mode (insn) == MODE_SI)
1889 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1891 return "mov{w}\t{%1, %0|%0, %1}";
1895 (cond [(ne (symbol_ref "optimize_function_for_size_p (cfun)") (const_int 0))
1896 (const_string "imov")
1897 (and (eq_attr "alternative" "0")
1898 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1900 (eq (symbol_ref "TARGET_HIMODE_MATH")
1902 (const_string "imov")
1903 (and (eq_attr "alternative" "1,2")
1904 (match_operand:HI 1 "aligned_operand" ""))
1905 (const_string "imov")
1906 (and (ne (symbol_ref "TARGET_MOVX")
1908 (eq_attr "alternative" "0,2"))
1909 (const_string "imovx")
1911 (const_string "imov")))
1913 (cond [(eq_attr "type" "imovx")
1915 (and (eq_attr "alternative" "1,2")
1916 (match_operand:HI 1 "aligned_operand" ""))
1918 (and (eq_attr "alternative" "0")
1919 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1921 (eq (symbol_ref "TARGET_HIMODE_MATH")
1925 (const_string "HI")))])
1927 ;; Stores and loads of ax to arbitrary constant address.
1928 ;; We fake an second form of instruction to force reload to load address
1929 ;; into register when rax is not available
1930 (define_insn "*movabshi_1_rex64"
1931 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1932 (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1933 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1935 movabs{w}\t{%1, %P0|%P0, %1}
1936 mov{w}\t{%1, %a0|%a0, %1}"
1937 [(set_attr "type" "imov")
1938 (set_attr "modrm" "0,*")
1939 (set_attr "length_address" "8,0")
1940 (set_attr "length_immediate" "0,*")
1941 (set_attr "memory" "store")
1942 (set_attr "mode" "HI")])
1944 (define_insn "*movabshi_2_rex64"
1945 [(set (match_operand:HI 0 "register_operand" "=a,r")
1946 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1947 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1949 movabs{w}\t{%P1, %0|%0, %P1}
1950 mov{w}\t{%a1, %0|%0, %a1}"
1951 [(set_attr "type" "imov")
1952 (set_attr "modrm" "0,*")
1953 (set_attr "length_address" "8,0")
1954 (set_attr "length_immediate" "0")
1955 (set_attr "memory" "load")
1956 (set_attr "mode" "HI")])
1958 (define_insn "*swaphi_1"
1959 [(set (match_operand:HI 0 "register_operand" "+r")
1960 (match_operand:HI 1 "register_operand" "+r"))
1963 "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
1965 [(set_attr "type" "imov")
1966 (set_attr "mode" "SI")
1967 (set_attr "pent_pair" "np")
1968 (set_attr "athlon_decode" "vector")
1969 (set_attr "amdfam10_decode" "double")])
1971 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
1972 (define_insn "*swaphi_2"
1973 [(set (match_operand:HI 0 "register_operand" "+r")
1974 (match_operand:HI 1 "register_operand" "+r"))
1977 "TARGET_PARTIAL_REG_STALL"
1979 [(set_attr "type" "imov")
1980 (set_attr "mode" "HI")
1981 (set_attr "pent_pair" "np")
1982 (set_attr "athlon_decode" "vector")])
1984 (define_expand "movstricthi"
1985 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1986 (match_operand:HI 1 "general_operand" ""))]
1989 if (TARGET_PARTIAL_REG_STALL && optimize_function_for_speed_p (cfun))
1991 /* Don't generate memory->memory moves, go through a register */
1992 if (MEM_P (operands[0]) && MEM_P (operands[1]))
1993 operands[1] = force_reg (HImode, operands[1]);
1996 (define_insn "*movstricthi_1"
1997 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1998 (match_operand:HI 1 "general_operand" "rn,m"))]
1999 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
2000 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2001 "mov{w}\t{%1, %0|%0, %1}"
2002 [(set_attr "type" "imov")
2003 (set_attr "mode" "HI")])
2005 (define_insn "*movstricthi_xor"
2006 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
2007 (match_operand:HI 1 "const0_operand" ""))
2008 (clobber (reg:CC FLAGS_REG))]
2011 [(set_attr "type" "alu1")
2012 (set_attr "mode" "HI")
2013 (set_attr "length_immediate" "0")])
2015 (define_expand "movqi"
2016 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2017 (match_operand:QI 1 "general_operand" ""))]
2019 "ix86_expand_move (QImode, operands); DONE;")
2021 ;; emit_push_insn when it calls move_by_pieces requires an insn to
2022 ;; "push a byte". But actually we use pushl, which has the effect
2023 ;; of rounding the amount pushed up to a word.
2025 (define_insn "*pushqi2"
2026 [(set (match_operand:QI 0 "push_operand" "=X")
2027 (match_operand:QI 1 "nonmemory_no_elim_operand" "rn"))]
2030 [(set_attr "type" "push")
2031 (set_attr "mode" "SI")])
2033 ;; For 64BIT abi we always round up to 8 bytes.
2034 (define_insn "*pushqi2_rex64"
2035 [(set (match_operand:QI 0 "push_operand" "=X")
2036 (match_operand:QI 1 "nonmemory_no_elim_operand" "qn"))]
2039 [(set_attr "type" "push")
2040 (set_attr "mode" "DI")])
2042 ;; Situation is quite tricky about when to choose full sized (SImode) move
2043 ;; over QImode moves. For Q_REG -> Q_REG move we use full size only for
2044 ;; partial register dependency machines (such as AMD Athlon), where QImode
2045 ;; moves issue extra dependency and for partial register stalls machines
2046 ;; that don't use QImode patterns (and QImode move cause stall on the next
2049 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
2050 ;; register stall machines with, where we use QImode instructions, since
2051 ;; partial register stall can be caused there. Then we use movzx.
2052 (define_insn "*movqi_1"
2053 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
2054 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,qm,qn"))]
2055 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2057 switch (get_attr_type (insn))
2060 gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
2061 return "movz{bl|x}\t{%1, %k0|%k0, %1}";
2063 if (get_attr_mode (insn) == MODE_SI)
2064 return "mov{l}\t{%k1, %k0|%k0, %k1}";
2066 return "mov{b}\t{%1, %0|%0, %1}";
2070 (cond [(and (eq_attr "alternative" "5")
2071 (not (match_operand:QI 1 "aligned_operand" "")))
2072 (const_string "imovx")
2073 (ne (symbol_ref "optimize_function_for_size_p (cfun)") (const_int 0))
2074 (const_string "imov")
2075 (and (eq_attr "alternative" "3")
2076 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
2078 (eq (symbol_ref "TARGET_QIMODE_MATH")
2080 (const_string "imov")
2081 (eq_attr "alternative" "3,5")
2082 (const_string "imovx")
2083 (and (ne (symbol_ref "TARGET_MOVX")
2085 (eq_attr "alternative" "2"))
2086 (const_string "imovx")
2088 (const_string "imov")))
2090 (cond [(eq_attr "alternative" "3,4,5")
2092 (eq_attr "alternative" "6")
2094 (eq_attr "type" "imovx")
2096 (and (eq_attr "type" "imov")
2097 (and (eq_attr "alternative" "0,1")
2098 (and (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
2100 (and (eq (symbol_ref "optimize_function_for_size_p (cfun)")
2102 (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
2105 ;; Avoid partial register stalls when not using QImode arithmetic
2106 (and (eq_attr "type" "imov")
2107 (and (eq_attr "alternative" "0,1")
2108 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
2110 (eq (symbol_ref "TARGET_QIMODE_MATH")
2114 (const_string "QI")))])
2116 (define_insn "*swapqi_1"
2117 [(set (match_operand:QI 0 "register_operand" "+r")
2118 (match_operand:QI 1 "register_operand" "+r"))
2121 "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
2123 [(set_attr "type" "imov")
2124 (set_attr "mode" "SI")
2125 (set_attr "pent_pair" "np")
2126 (set_attr "athlon_decode" "vector")
2127 (set_attr "amdfam10_decode" "vector")])
2129 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
2130 (define_insn "*swapqi_2"
2131 [(set (match_operand:QI 0 "register_operand" "+q")
2132 (match_operand:QI 1 "register_operand" "+q"))
2135 "TARGET_PARTIAL_REG_STALL"
2137 [(set_attr "type" "imov")
2138 (set_attr "mode" "QI")
2139 (set_attr "pent_pair" "np")
2140 (set_attr "athlon_decode" "vector")])
2142 (define_expand "movstrictqi"
2143 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
2144 (match_operand:QI 1 "general_operand" ""))]
2147 if (TARGET_PARTIAL_REG_STALL && optimize_function_for_speed_p (cfun))
2149 /* Don't generate memory->memory moves, go through a register. */
2150 if (MEM_P (operands[0]) && MEM_P (operands[1]))
2151 operands[1] = force_reg (QImode, operands[1]);
2154 (define_insn "*movstrictqi_1"
2155 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
2156 (match_operand:QI 1 "general_operand" "*qn,m"))]
2157 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
2158 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2159 "mov{b}\t{%1, %0|%0, %1}"
2160 [(set_attr "type" "imov")
2161 (set_attr "mode" "QI")])
2163 (define_insn "*movstrictqi_xor"
2164 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
2165 (match_operand:QI 1 "const0_operand" ""))
2166 (clobber (reg:CC FLAGS_REG))]
2169 [(set_attr "type" "alu1")
2170 (set_attr "mode" "QI")
2171 (set_attr "length_immediate" "0")])
2173 (define_insn "*movsi_extv_1"
2174 [(set (match_operand:SI 0 "register_operand" "=R")
2175 (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
2179 "movs{bl|x}\t{%h1, %0|%0, %h1}"
2180 [(set_attr "type" "imovx")
2181 (set_attr "mode" "SI")])
2183 (define_insn "*movhi_extv_1"
2184 [(set (match_operand:HI 0 "register_operand" "=R")
2185 (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
2189 "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
2190 [(set_attr "type" "imovx")
2191 (set_attr "mode" "SI")])
2193 (define_insn "*movqi_extv_1"
2194 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
2195 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2200 switch (get_attr_type (insn))
2203 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2205 return "mov{b}\t{%h1, %0|%0, %h1}";
2209 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2210 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2211 (ne (symbol_ref "TARGET_MOVX")
2213 (const_string "imovx")
2214 (const_string "imov")))
2216 (if_then_else (eq_attr "type" "imovx")
2218 (const_string "QI")))])
2220 (define_insn "*movqi_extv_1_rex64"
2221 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2222 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2227 switch (get_attr_type (insn))
2230 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2232 return "mov{b}\t{%h1, %0|%0, %h1}";
2236 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2237 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2238 (ne (symbol_ref "TARGET_MOVX")
2240 (const_string "imovx")
2241 (const_string "imov")))
2243 (if_then_else (eq_attr "type" "imovx")
2245 (const_string "QI")))])
2247 ;; Stores and loads of ax to arbitrary constant address.
2248 ;; We fake an second form of instruction to force reload to load address
2249 ;; into register when rax is not available
2250 (define_insn "*movabsqi_1_rex64"
2251 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2252 (match_operand:QI 1 "nonmemory_operand" "a,er"))]
2253 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2255 movabs{b}\t{%1, %P0|%P0, %1}
2256 mov{b}\t{%1, %a0|%a0, %1}"
2257 [(set_attr "type" "imov")
2258 (set_attr "modrm" "0,*")
2259 (set_attr "length_address" "8,0")
2260 (set_attr "length_immediate" "0,*")
2261 (set_attr "memory" "store")
2262 (set_attr "mode" "QI")])
2264 (define_insn "*movabsqi_2_rex64"
2265 [(set (match_operand:QI 0 "register_operand" "=a,r")
2266 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2267 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2269 movabs{b}\t{%P1, %0|%0, %P1}
2270 mov{b}\t{%a1, %0|%0, %a1}"
2271 [(set_attr "type" "imov")
2272 (set_attr "modrm" "0,*")
2273 (set_attr "length_address" "8,0")
2274 (set_attr "length_immediate" "0")
2275 (set_attr "memory" "load")
2276 (set_attr "mode" "QI")])
2278 (define_insn "*movdi_extzv_1"
2279 [(set (match_operand:DI 0 "register_operand" "=R")
2280 (zero_extract:DI (match_operand 1 "ext_register_operand" "Q")
2284 "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
2285 [(set_attr "type" "imovx")
2286 (set_attr "mode" "DI")])
2288 (define_insn "*movsi_extzv_1"
2289 [(set (match_operand:SI 0 "register_operand" "=R")
2290 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
2294 "movz{bl|x}\t{%h1, %0|%0, %h1}"
2295 [(set_attr "type" "imovx")
2296 (set_attr "mode" "SI")])
2298 (define_insn "*movqi_extzv_2"
2299 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2300 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2305 switch (get_attr_type (insn))
2308 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2310 return "mov{b}\t{%h1, %0|%0, %h1}";
2314 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2315 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2316 (ne (symbol_ref "TARGET_MOVX")
2318 (const_string "imovx")
2319 (const_string "imov")))
2321 (if_then_else (eq_attr "type" "imovx")
2323 (const_string "QI")))])
2325 (define_insn "*movqi_extzv_2_rex64"
2326 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2327 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2332 switch (get_attr_type (insn))
2335 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2337 return "mov{b}\t{%h1, %0|%0, %h1}";
2341 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2342 (ne (symbol_ref "TARGET_MOVX")
2344 (const_string "imovx")
2345 (const_string "imov")))
2347 (if_then_else (eq_attr "type" "imovx")
2349 (const_string "QI")))])
2351 (define_insn "movsi_insv_1"
2352 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2355 (match_operand:SI 1 "general_operand" "Qmn"))]
2357 "mov{b}\t{%b1, %h0|%h0, %b1}"
2358 [(set_attr "type" "imov")
2359 (set_attr "mode" "QI")])
2361 (define_insn "*movsi_insv_1_rex64"
2362 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2365 (match_operand:SI 1 "nonmemory_operand" "Qn"))]
2367 "mov{b}\t{%b1, %h0|%h0, %b1}"
2368 [(set_attr "type" "imov")
2369 (set_attr "mode" "QI")])
2371 (define_insn "movdi_insv_1_rex64"
2372 [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
2375 (match_operand:DI 1 "nonmemory_operand" "Qn"))]
2377 "mov{b}\t{%b1, %h0|%h0, %b1}"
2378 [(set_attr "type" "imov")
2379 (set_attr "mode" "QI")])
2381 (define_insn "*movqi_insv_2"
2382 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2385 (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2388 "mov{b}\t{%h1, %h0|%h0, %h1}"
2389 [(set_attr "type" "imov")
2390 (set_attr "mode" "QI")])
2392 (define_expand "movdi"
2393 [(set (match_operand:DI 0 "nonimmediate_operand" "")
2394 (match_operand:DI 1 "general_operand" ""))]
2396 "ix86_expand_move (DImode, operands); DONE;")
2398 (define_insn "*pushdi"
2399 [(set (match_operand:DI 0 "push_operand" "=<")
2400 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
2404 (define_insn "*pushdi2_rex64"
2405 [(set (match_operand:DI 0 "push_operand" "=<,!<")
2406 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
2411 [(set_attr "type" "push,multi")
2412 (set_attr "mode" "DI")])
2414 ;; Convert impossible pushes of immediate to existing instructions.
2415 ;; First try to get scratch register and go through it. In case this
2416 ;; fails, push sign extended lower part first and then overwrite
2417 ;; upper part by 32bit move.
2419 [(match_scratch:DI 2 "r")
2420 (set (match_operand:DI 0 "push_operand" "")
2421 (match_operand:DI 1 "immediate_operand" ""))]
2422 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2423 && !x86_64_immediate_operand (operands[1], DImode)"
2424 [(set (match_dup 2) (match_dup 1))
2425 (set (match_dup 0) (match_dup 2))]
2428 ;; We need to define this as both peepholer and splitter for case
2429 ;; peephole2 pass is not run.
2430 ;; "&& 1" is needed to keep it from matching the previous pattern.
2432 [(set (match_operand:DI 0 "push_operand" "")
2433 (match_operand:DI 1 "immediate_operand" ""))]
2434 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2435 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2436 [(set (match_dup 0) (match_dup 1))
2437 (set (match_dup 2) (match_dup 3))]
2438 "split_di (&operands[1], 1, &operands[2], &operands[3]);
2439 operands[1] = gen_lowpart (DImode, operands[2]);
2440 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2445 [(set (match_operand:DI 0 "push_operand" "")
2446 (match_operand:DI 1 "immediate_operand" ""))]
2447 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2448 ? epilogue_completed : reload_completed)
2449 && !symbolic_operand (operands[1], DImode)
2450 && !x86_64_immediate_operand (operands[1], DImode)"
2451 [(set (match_dup 0) (match_dup 1))
2452 (set (match_dup 2) (match_dup 3))]
2453 "split_di (&operands[1], 1, &operands[2], &operands[3]);
2454 operands[1] = gen_lowpart (DImode, operands[2]);
2455 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2459 (define_insn "*pushdi2_prologue_rex64"
2460 [(set (match_operand:DI 0 "push_operand" "=<")
2461 (match_operand:DI 1 "general_no_elim_operand" "re*m"))
2462 (clobber (mem:BLK (scratch)))]
2465 [(set_attr "type" "push")
2466 (set_attr "mode" "DI")])
2468 (define_insn "*popdi1_epilogue_rex64"
2469 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2470 (mem:DI (reg:DI SP_REG)))
2471 (set (reg:DI SP_REG)
2472 (plus:DI (reg:DI SP_REG) (const_int 8)))
2473 (clobber (mem:BLK (scratch)))]
2476 [(set_attr "type" "pop")
2477 (set_attr "mode" "DI")])
2479 (define_insn "popdi1"
2480 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2481 (mem:DI (reg:DI SP_REG)))
2482 (set (reg:DI SP_REG)
2483 (plus:DI (reg:DI SP_REG) (const_int 8)))]
2486 [(set_attr "type" "pop")
2487 (set_attr "mode" "DI")])
2489 (define_insn "*movdi_xor_rex64"
2490 [(set (match_operand:DI 0 "register_operand" "=r")
2491 (match_operand:DI 1 "const0_operand" ""))
2492 (clobber (reg:CC FLAGS_REG))]
2494 && reload_completed"
2496 [(set_attr "type" "alu1")
2497 (set_attr "mode" "SI")
2498 (set_attr "length_immediate" "0")])
2500 (define_insn "*movdi_or_rex64"
2501 [(set (match_operand:DI 0 "register_operand" "=r")
2502 (match_operand:DI 1 "const_int_operand" "i"))
2503 (clobber (reg:CC FLAGS_REG))]
2506 && operands[1] == constm1_rtx"
2508 operands[1] = constm1_rtx;
2509 return "or{q}\t{%1, %0|%0, %1}";
2511 [(set_attr "type" "alu1")
2512 (set_attr "mode" "DI")
2513 (set_attr "length_immediate" "1")])
2515 (define_insn "*movdi_2"
2516 [(set (match_operand:DI 0 "nonimmediate_operand"
2517 "=r ,o ,*y,m*y,*y,*Y2,m ,*Y2,*Y2,*x,m ,*x,*x")
2518 (match_operand:DI 1 "general_operand"
2519 "riFo,riF,C ,*y ,m ,C ,*Y2,*Y2,m ,C ,*x,*x,m "))]
2520 "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2525 movq\t{%1, %0|%0, %1}
2526 movq\t{%1, %0|%0, %1}
2528 %vmovq\t{%1, %0|%0, %1}
2529 %vmovdqa\t{%1, %0|%0, %1}
2530 %vmovq\t{%1, %0|%0, %1}
2532 movlps\t{%1, %0|%0, %1}
2533 movaps\t{%1, %0|%0, %1}
2534 movlps\t{%1, %0|%0, %1}"
2535 [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
2536 (set (attr "prefix")
2537 (if_then_else (eq_attr "alternative" "5,6,7,8")
2538 (const_string "vex")
2539 (const_string "orig")))
2540 (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
2543 [(set (match_operand:DI 0 "push_operand" "")
2544 (match_operand:DI 1 "general_operand" ""))]
2545 "!TARGET_64BIT && reload_completed
2546 && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2548 "ix86_split_long_move (operands); DONE;")
2550 ;; %%% This multiword shite has got to go.
2552 [(set (match_operand:DI 0 "nonimmediate_operand" "")
2553 (match_operand:DI 1 "general_operand" ""))]
2554 "!TARGET_64BIT && reload_completed
2555 && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
2556 && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2558 "ix86_split_long_move (operands); DONE;")
2560 (define_insn "*movdi_1_rex64"
2561 [(set (match_operand:DI 0 "nonimmediate_operand"
2562 "=r,r ,r,m ,!m,*y,*y,?r ,m ,?*Ym,?*y,*x,*x,?r ,m,?*Yi,*x,?*x,?*Ym")
2563 (match_operand:DI 1 "general_operand"
2564 "Z ,rem,i,re,n ,C ,*y,*Ym,*y,r ,m ,C ,*x,*Yi,*x,r ,m ,*Ym,*x"))]
2565 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2567 switch (get_attr_type (insn))
2570 if (SSE_REG_P (operands[0]))
2571 return "movq2dq\t{%1, %0|%0, %1}";
2573 return "movdq2q\t{%1, %0|%0, %1}";
2578 if (get_attr_mode (insn) == MODE_TI)
2579 return "vmovdqa\t{%1, %0|%0, %1}";
2581 return "vmovq\t{%1, %0|%0, %1}";
2584 if (get_attr_mode (insn) == MODE_TI)
2585 return "movdqa\t{%1, %0|%0, %1}";
2589 /* Moves from and into integer register is done using movd
2590 opcode with REX prefix. */
2591 if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
2592 return "movd\t{%1, %0|%0, %1}";
2593 return "movq\t{%1, %0|%0, %1}";
2596 return "%vpxor\t%0, %d0";
2599 return "pxor\t%0, %0";
2605 return "lea{q}\t{%a1, %0|%0, %a1}";
2608 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2609 if (get_attr_mode (insn) == MODE_SI)
2610 return "mov{l}\t{%k1, %k0|%k0, %k1}";
2611 else if (which_alternative == 2)
2612 return "movabs{q}\t{%1, %0|%0, %1}";
2614 return "mov{q}\t{%1, %0|%0, %1}";
2618 (cond [(eq_attr "alternative" "5")
2619 (const_string "mmx")
2620 (eq_attr "alternative" "6,7,8,9,10")
2621 (const_string "mmxmov")
2622 (eq_attr "alternative" "11")
2623 (const_string "sselog1")
2624 (eq_attr "alternative" "12,13,14,15,16")
2625 (const_string "ssemov")
2626 (eq_attr "alternative" "17,18")
2627 (const_string "ssecvt")
2628 (eq_attr "alternative" "4")
2629 (const_string "multi")
2630 (match_operand:DI 1 "pic_32bit_operand" "")
2631 (const_string "lea")
2633 (const_string "imov")))
2634 (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2635 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2636 (set (attr "prefix")
2637 (if_then_else (eq_attr "alternative" "11,12,13,14,15,16")
2638 (const_string "maybe_vex")
2639 (const_string "orig")))
2640 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI,DI,DI")])
2642 ;; Stores and loads of ax to arbitrary constant address.
2643 ;; We fake an second form of instruction to force reload to load address
2644 ;; into register when rax is not available
2645 (define_insn "*movabsdi_1_rex64"
2646 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2647 (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2648 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2650 movabs{q}\t{%1, %P0|%P0, %1}
2651 mov{q}\t{%1, %a0|%a0, %1}"
2652 [(set_attr "type" "imov")
2653 (set_attr "modrm" "0,*")
2654 (set_attr "length_address" "8,0")
2655 (set_attr "length_immediate" "0,*")
2656 (set_attr "memory" "store")
2657 (set_attr "mode" "DI")])
2659 (define_insn "*movabsdi_2_rex64"
2660 [(set (match_operand:DI 0 "register_operand" "=a,r")
2661 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2662 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2664 movabs{q}\t{%P1, %0|%0, %P1}
2665 mov{q}\t{%a1, %0|%0, %a1}"
2666 [(set_attr "type" "imov")
2667 (set_attr "modrm" "0,*")
2668 (set_attr "length_address" "8,0")
2669 (set_attr "length_immediate" "0")
2670 (set_attr "memory" "load")
2671 (set_attr "mode" "DI")])
2673 ;; Convert impossible stores of immediate to existing instructions.
2674 ;; First try to get scratch register and go through it. In case this
2675 ;; fails, move by 32bit parts.
2677 [(match_scratch:DI 2 "r")
2678 (set (match_operand:DI 0 "memory_operand" "")
2679 (match_operand:DI 1 "immediate_operand" ""))]
2680 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2681 && !x86_64_immediate_operand (operands[1], DImode)"
2682 [(set (match_dup 2) (match_dup 1))
2683 (set (match_dup 0) (match_dup 2))]
2686 ;; We need to define this as both peepholer and splitter for case
2687 ;; peephole2 pass is not run.
2688 ;; "&& 1" is needed to keep it from matching the previous pattern.
2690 [(set (match_operand:DI 0 "memory_operand" "")
2691 (match_operand:DI 1 "immediate_operand" ""))]
2692 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2693 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2694 [(set (match_dup 2) (match_dup 3))
2695 (set (match_dup 4) (match_dup 5))]
2696 "split_di (&operands[0], 2, &operands[2], &operands[4]);")
2699 [(set (match_operand:DI 0 "memory_operand" "")
2700 (match_operand:DI 1 "immediate_operand" ""))]
2701 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2702 ? epilogue_completed : reload_completed)
2703 && !symbolic_operand (operands[1], DImode)
2704 && !x86_64_immediate_operand (operands[1], DImode)"
2705 [(set (match_dup 2) (match_dup 3))
2706 (set (match_dup 4) (match_dup 5))]
2707 "split_di (&operands[0], 2, &operands[2], &operands[4]);")
2709 (define_insn "*swapdi_rex64"
2710 [(set (match_operand:DI 0 "register_operand" "+r")
2711 (match_operand:DI 1 "register_operand" "+r"))
2716 [(set_attr "type" "imov")
2717 (set_attr "mode" "DI")
2718 (set_attr "pent_pair" "np")
2719 (set_attr "athlon_decode" "vector")
2720 (set_attr "amdfam10_decode" "double")])
2722 (define_expand "movoi"
2723 [(set (match_operand:OI 0 "nonimmediate_operand" "")
2724 (match_operand:OI 1 "general_operand" ""))]
2726 "ix86_expand_move (OImode, operands); DONE;")
2728 (define_insn "*movoi_internal"
2729 [(set (match_operand:OI 0 "nonimmediate_operand" "=x,x,m")
2730 (match_operand:OI 1 "vector_move_operand" "C,xm,x"))]
2732 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2734 switch (which_alternative)
2737 return "vxorps\t%0, %0, %0";
2740 if (misaligned_operand (operands[0], OImode)
2741 || misaligned_operand (operands[1], OImode))
2742 return "vmovdqu\t{%1, %0|%0, %1}";
2744 return "vmovdqa\t{%1, %0|%0, %1}";
2749 [(set_attr "type" "sselog1,ssemov,ssemov")
2750 (set_attr "prefix" "vex")
2751 (set_attr "mode" "OI")])
2753 (define_expand "movti"
2754 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2755 (match_operand:TI 1 "nonimmediate_operand" ""))]
2756 "TARGET_SSE || TARGET_64BIT"
2759 ix86_expand_move (TImode, operands);
2760 else if (push_operand (operands[0], TImode))
2761 ix86_expand_push (TImode, operands[1]);
2763 ix86_expand_vector_move (TImode, operands);
2767 (define_insn "*movti_internal"
2768 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2769 (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2770 "TARGET_SSE && !TARGET_64BIT
2771 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2773 switch (which_alternative)
2776 if (get_attr_mode (insn) == MODE_V4SF)
2777 return "%vxorps\t%0, %d0";
2779 return "%vpxor\t%0, %d0";
2782 /* TDmode values are passed as TImode on the stack. Moving them
2783 to stack may result in unaligned memory access. */
2784 if (misaligned_operand (operands[0], TImode)
2785 || misaligned_operand (operands[1], TImode))
2787 if (get_attr_mode (insn) == MODE_V4SF)
2788 return "%vmovups\t{%1, %0|%0, %1}";
2790 return "%vmovdqu\t{%1, %0|%0, %1}";
2794 if (get_attr_mode (insn) == MODE_V4SF)
2795 return "%vmovaps\t{%1, %0|%0, %1}";
2797 return "%vmovdqa\t{%1, %0|%0, %1}";
2803 [(set_attr "type" "sselog1,ssemov,ssemov")
2804 (set_attr "prefix" "maybe_vex")
2806 (cond [(ior (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2807 (ne (symbol_ref "optimize_function_for_size_p (cfun)") (const_int 0)))
2808 (const_string "V4SF")
2809 (and (eq_attr "alternative" "2")
2810 (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2812 (const_string "V4SF")]
2813 (const_string "TI")))])
2815 (define_insn "*movti_rex64"
2816 [(set (match_operand:TI 0 "nonimmediate_operand" "=!r,o,x,x,xm")
2817 (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2819 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2821 switch (which_alternative)
2827 if (get_attr_mode (insn) == MODE_V4SF)
2828 return "%vxorps\t%0, %d0";
2830 return "%vpxor\t%0, %d0";
2833 /* TDmode values are passed as TImode on the stack. Moving them
2834 to stack may result in unaligned memory access. */
2835 if (misaligned_operand (operands[0], TImode)
2836 || misaligned_operand (operands[1], TImode))
2838 if (get_attr_mode (insn) == MODE_V4SF)
2839 return "%vmovups\t{%1, %0|%0, %1}";
2841 return "%vmovdqu\t{%1, %0|%0, %1}";
2845 if (get_attr_mode (insn) == MODE_V4SF)
2846 return "%vmovaps\t{%1, %0|%0, %1}";
2848 return "%vmovdqa\t{%1, %0|%0, %1}";
2854 [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
2855 (set_attr "prefix" "*,*,maybe_vex,maybe_vex,maybe_vex")
2857 (cond [(eq_attr "alternative" "2,3")
2859 (ne (symbol_ref "optimize_function_for_size_p (cfun)")
2861 (const_string "V4SF")
2862 (const_string "TI"))
2863 (eq_attr "alternative" "4")
2865 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2867 (ne (symbol_ref "optimize_function_for_size_p (cfun)")
2869 (const_string "V4SF")
2870 (const_string "TI"))]
2871 (const_string "DI")))])
2874 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2875 (match_operand:TI 1 "general_operand" ""))]
2876 "reload_completed && !SSE_REG_P (operands[0])
2877 && !SSE_REG_P (operands[1])"
2879 "ix86_split_long_move (operands); DONE;")
2881 ;; This expands to what emit_move_complex would generate if we didn't
2882 ;; have a movti pattern. Having this avoids problems with reload on
2883 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
2884 ;; to have around all the time.
2885 (define_expand "movcdi"
2886 [(set (match_operand:CDI 0 "nonimmediate_operand" "")
2887 (match_operand:CDI 1 "general_operand" ""))]
2890 if (push_operand (operands[0], CDImode))
2891 emit_move_complex_push (CDImode, operands[0], operands[1]);
2893 emit_move_complex_parts (operands[0], operands[1]);
2897 (define_expand "movsf"
2898 [(set (match_operand:SF 0 "nonimmediate_operand" "")
2899 (match_operand:SF 1 "general_operand" ""))]
2901 "ix86_expand_move (SFmode, operands); DONE;")
2903 (define_insn "*pushsf"
2904 [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2905 (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2908 /* Anything else should be already split before reg-stack. */
2909 gcc_assert (which_alternative == 1);
2910 return "push{l}\t%1";
2912 [(set_attr "type" "multi,push,multi")
2913 (set_attr "unit" "i387,*,*")
2914 (set_attr "mode" "SF,SI,SF")])
2916 (define_insn "*pushsf_rex64"
2917 [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2918 (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2921 /* Anything else should be already split before reg-stack. */
2922 gcc_assert (which_alternative == 1);
2923 return "push{q}\t%q1";
2925 [(set_attr "type" "multi,push,multi")
2926 (set_attr "unit" "i387,*,*")
2927 (set_attr "mode" "SF,DI,SF")])
2930 [(set (match_operand:SF 0 "push_operand" "")
2931 (match_operand:SF 1 "memory_operand" ""))]
2933 && MEM_P (operands[1])
2934 && (operands[2] = find_constant_src (insn))"
2939 ;; %%% Kill this when call knows how to work this out.
2941 [(set (match_operand:SF 0 "push_operand" "")
2942 (match_operand:SF 1 "any_fp_register_operand" ""))]
2944 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2945 (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2948 [(set (match_operand:SF 0 "push_operand" "")
2949 (match_operand:SF 1 "any_fp_register_operand" ""))]
2951 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2952 (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2954 (define_insn "*movsf_1"
2955 [(set (match_operand:SF 0 "nonimmediate_operand"
2956 "=f,m,f,r ,m ,x,x,x ,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
2957 (match_operand:SF 1 "general_operand"
2958 "fm,f,G,rmF,Fr,C,x,xm,x,m ,*y,*y ,r ,Yi,r ,*Ym"))]
2959 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2960 && (reload_in_progress || reload_completed
2961 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2962 || (!TARGET_SSE_MATH && optimize_function_for_size_p (cfun)
2963 && standard_80387_constant_p (operands[1]))
2964 || GET_CODE (operands[1]) != CONST_DOUBLE
2965 || memory_operand (operands[0], SFmode))"
2967 switch (which_alternative)
2971 return output_387_reg_move (insn, operands);
2974 return standard_80387_constant_opcode (operands[1]);
2978 return "mov{l}\t{%1, %0|%0, %1}";
2980 if (get_attr_mode (insn) == MODE_TI)
2981 return "%vpxor\t%0, %d0";
2983 return "%vxorps\t%0, %d0";
2985 if (get_attr_mode (insn) == MODE_V4SF)
2986 return "%vmovaps\t{%1, %0|%0, %1}";
2988 return "%vmovss\t{%1, %d0|%d0, %1}";
2991 return REG_P (operands[1]) ? "vmovss\t{%1, %0, %0|%0, %0, %1}"
2992 : "vmovss\t{%1, %0|%0, %1}";
2994 return "movss\t{%1, %0|%0, %1}";
2996 return "%vmovss\t{%1, %0|%0, %1}";
2998 case 9: case 10: case 14: case 15:
2999 return "movd\t{%1, %0|%0, %1}";
3001 return "%vmovd\t{%1, %0|%0, %1}";
3004 return "movq\t{%1, %0|%0, %1}";
3010 [(set_attr "type" "fmov,fmov,fmov,imov,imov,sselog1,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov,ssemov,ssemov,mmxmov,mmxmov")
3011 (set (attr "prefix")
3012 (if_then_else (eq_attr "alternative" "5,6,7,8,12,13")
3013 (const_string "maybe_vex")
3014 (const_string "orig")))
3016 (cond [(eq_attr "alternative" "3,4,9,10")
3018 (eq_attr "alternative" "5")
3020 (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3022 (ne (symbol_ref "TARGET_SSE2")
3024 (eq (symbol_ref "optimize_function_for_size_p (cfun)")
3027 (const_string "V4SF"))
3028 /* For architectures resolving dependencies on
3029 whole SSE registers use APS move to break dependency
3030 chains, otherwise use short move to avoid extra work.
3032 Do the same for architectures resolving dependencies on
3033 the parts. While in DF mode it is better to always handle
3034 just register parts, the SF mode is different due to lack
3035 of instructions to load just part of the register. It is
3036 better to maintain the whole registers in single format
3037 to avoid problems on using packed logical operations. */
3038 (eq_attr "alternative" "6")
3040 (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3042 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3044 (const_string "V4SF")
3045 (const_string "SF"))
3046 (eq_attr "alternative" "11")
3047 (const_string "DI")]
3048 (const_string "SF")))])
3050 (define_insn "*swapsf"
3051 [(set (match_operand:SF 0 "fp_register_operand" "+f")
3052 (match_operand:SF 1 "fp_register_operand" "+f"))
3055 "reload_completed || TARGET_80387"
3057 if (STACK_TOP_P (operands[0]))
3062 [(set_attr "type" "fxch")
3063 (set_attr "mode" "SF")])
3065 (define_expand "movdf"
3066 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3067 (match_operand:DF 1 "general_operand" ""))]
3069 "ix86_expand_move (DFmode, operands); DONE;")
3071 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
3072 ;; Size of pushdf using integer instructions is 2+2*memory operand size
3073 ;; On the average, pushdf using integers can be still shorter. Allow this
3074 ;; pattern for optimize_size too.
3076 (define_insn "*pushdf_nointeger"
3077 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
3078 (match_operand:DF 1 "general_no_elim_operand" "f,Fo,*r,Y2"))]
3079 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
3081 /* This insn should be already split before reg-stack. */
3084 [(set_attr "type" "multi")
3085 (set_attr "unit" "i387,*,*,*")
3086 (set_attr "mode" "DF,SI,SI,DF")])
3088 (define_insn "*pushdf_integer"
3089 [(set (match_operand:DF 0 "push_operand" "=<,<,<")
3090 (match_operand:DF 1 "general_no_elim_operand" "f,rFo,Y2"))]
3091 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
3093 /* This insn should be already split before reg-stack. */
3096 [(set_attr "type" "multi")
3097 (set_attr "unit" "i387,*,*")
3098 (set_attr "mode" "DF,SI,DF")])
3100 ;; %%% Kill this when call knows how to work this out.
3102 [(set (match_operand:DF 0 "push_operand" "")
3103 (match_operand:DF 1 "any_fp_register_operand" ""))]
3105 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
3106 (set (mem:DF (reg:P SP_REG)) (match_dup 1))]
3110 [(set (match_operand:DF 0 "push_operand" "")
3111 (match_operand:DF 1 "general_operand" ""))]
3114 "ix86_split_long_move (operands); DONE;")
3116 ;; Moving is usually shorter when only FP registers are used. This separate
3117 ;; movdf pattern avoids the use of integer registers for FP operations
3118 ;; when optimizing for size.
3120 (define_insn "*movdf_nointeger"
3121 [(set (match_operand:DF 0 "nonimmediate_operand"
3122 "=f,m,f,*r ,o ,Y2*x,Y2*x,Y2*x ,m ")
3123 (match_operand:DF 1 "general_operand"
3124 "fm,f,G,*roF,*Fr,C ,Y2*x,mY2*x,Y2*x"))]
3125 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3126 && ((optimize_function_for_size_p (cfun)
3127 || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
3128 && (reload_in_progress || reload_completed
3129 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3130 || (!(TARGET_SSE2 && TARGET_SSE_MATH)
3131 && optimize_function_for_size_p (cfun)
3132 && !memory_operand (operands[0], DFmode)
3133 && standard_80387_constant_p (operands[1]))
3134 || GET_CODE (operands[1]) != CONST_DOUBLE
3135 || ((optimize_function_for_size_p (cfun)
3136 || !TARGET_MEMORY_MISMATCH_STALL
3137 || reload_in_progress || reload_completed)
3138 && memory_operand (operands[0], DFmode)))"
3140 switch (which_alternative)
3144 return output_387_reg_move (insn, operands);
3147 return standard_80387_constant_opcode (operands[1]);
3153 switch (get_attr_mode (insn))
3156 return "%vxorps\t%0, %d0";
3158 return "%vxorpd\t%0, %d0";
3160 return "%vpxor\t%0, %d0";
3167 switch (get_attr_mode (insn))
3170 return "%vmovaps\t{%1, %0|%0, %1}";
3172 return "%vmovapd\t{%1, %0|%0, %1}";
3174 return "%vmovdqa\t{%1, %0|%0, %1}";
3176 return "%vmovq\t{%1, %0|%0, %1}";
3180 if (REG_P (operands[0]) && REG_P (operands[1]))
3181 return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3183 return "vmovsd\t{%1, %0|%0, %1}";
3186 return "movsd\t{%1, %0|%0, %1}";
3190 if (REG_P (operands[0]))
3191 return "vmovlpd\t{%1, %0, %0|%0, %0, %1}";
3193 return "vmovlpd\t{%1, %0|%0, %1}";
3196 return "movlpd\t{%1, %0|%0, %1}";
3200 if (REG_P (operands[0]))
3201 return "vmovlps\t{%1, %0, %0|%0, %0, %1}";
3203 return "vmovlps\t{%1, %0|%0, %1}";
3206 return "movlps\t{%1, %0|%0, %1}";
3215 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
3216 (set (attr "prefix")
3217 (if_then_else (eq_attr "alternative" "0,1,2,3,4")
3218 (const_string "orig")
3219 (const_string "maybe_vex")))
3221 (cond [(eq_attr "alternative" "0,1,2")
3223 (eq_attr "alternative" "3,4")
3226 /* For SSE1, we have many fewer alternatives. */
3227 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
3228 (cond [(eq_attr "alternative" "5,6")
3229 (const_string "V4SF")
3231 (const_string "V2SF"))
3233 /* xorps is one byte shorter. */
3234 (eq_attr "alternative" "5")
3235 (cond [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3237 (const_string "V4SF")
3238 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3242 (const_string "V2DF"))
3244 /* For architectures resolving dependencies on
3245 whole SSE registers use APD move to break dependency
3246 chains, otherwise use short move to avoid extra work.
3248 movaps encodes one byte shorter. */
3249 (eq_attr "alternative" "6")
3251 [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3253 (const_string "V4SF")
3254 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3256 (const_string "V2DF")
3258 (const_string "DF"))
3259 /* For architectures resolving dependencies on register
3260 parts we may avoid extra work to zero out upper part
3262 (eq_attr "alternative" "7")
3264 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3266 (const_string "V1DF")
3267 (const_string "DF"))
3269 (const_string "DF")))])
3271 (define_insn "*movdf_integer_rex64"
3272 [(set (match_operand:DF 0 "nonimmediate_operand"
3273 "=f,m,f,r ,m ,Y2*x,Y2*x,Y2*x,m ,Yi,r ")
3274 (match_operand:DF 1 "general_operand"
3275 "fm,f,G,rmF,Fr,C ,Y2*x,m ,Y2*x,r ,Yi"))]
3276 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3277 && (reload_in_progress || reload_completed
3278 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3279 || (!(TARGET_SSE2 && TARGET_SSE_MATH)
3280 && optimize_function_for_size_p (cfun)
3281 && standard_80387_constant_p (operands[1]))
3282 || GET_CODE (operands[1]) != CONST_DOUBLE
3283 || memory_operand (operands[0], DFmode))"
3285 switch (which_alternative)
3289 return output_387_reg_move (insn, operands);
3292 return standard_80387_constant_opcode (operands[1]);
3299 switch (get_attr_mode (insn))
3302 return "%vxorps\t%0, %d0";
3304 return "%vxorpd\t%0, %d0";
3306 return "%vpxor\t%0, %d0";
3313 switch (get_attr_mode (insn))
3316 return "%vmovaps\t{%1, %0|%0, %1}";
3318 return "%vmovapd\t{%1, %0|%0, %1}";
3320 return "%vmovdqa\t{%1, %0|%0, %1}";
3322 return "%vmovq\t{%1, %0|%0, %1}";
3326 if (REG_P (operands[0]) && REG_P (operands[1]))
3327 return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3329 return "vmovsd\t{%1, %0|%0, %1}";
3332 return "movsd\t{%1, %0|%0, %1}";
3334 return "%vmovlpd\t{%1, %d0|%d0, %1}";
3336 return "%vmovlps\t{%1, %d0|%d0, %1}";
3343 return "%vmovd\t{%1, %0|%0, %1}";
3349 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov,ssemov,ssemov")
3350 (set (attr "prefix")
3351 (if_then_else (eq_attr "alternative" "0,1,2,3,4")
3352 (const_string "orig")
3353 (const_string "maybe_vex")))
3355 (cond [(eq_attr "alternative" "0,1,2")
3357 (eq_attr "alternative" "3,4,9,10")
3360 /* For SSE1, we have many fewer alternatives. */
3361 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
3362 (cond [(eq_attr "alternative" "5,6")
3363 (const_string "V4SF")
3365 (const_string "V2SF"))
3367 /* xorps is one byte shorter. */
3368 (eq_attr "alternative" "5")
3369 (cond [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3371 (const_string "V4SF")
3372 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3376 (const_string "V2DF"))
3378 /* For architectures resolving dependencies on
3379 whole SSE registers use APD move to break dependency
3380 chains, otherwise use short move to avoid extra work.
3382 movaps encodes one byte shorter. */
3383 (eq_attr "alternative" "6")
3385 [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3387 (const_string "V4SF")
3388 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3390 (const_string "V2DF")
3392 (const_string "DF"))
3393 /* For architectures resolving dependencies on register
3394 parts we may avoid extra work to zero out upper part
3396 (eq_attr "alternative" "7")
3398 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3400 (const_string "V1DF")
3401 (const_string "DF"))
3403 (const_string "DF")))])
3405 (define_insn "*movdf_integer"
3406 [(set (match_operand:DF 0 "nonimmediate_operand"
3407 "=f,m,f,r ,o ,Y2*x,Y2*x,Y2*x,m ")
3408 (match_operand:DF 1 "general_operand"
3409 "fm,f,G,roF,Fr,C ,Y2*x,m ,Y2*x"))]
3410 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3411 && optimize_function_for_speed_p (cfun)
3412 && TARGET_INTEGER_DFMODE_MOVES
3413 && (reload_in_progress || reload_completed
3414 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3415 || (!(TARGET_SSE2 && TARGET_SSE_MATH)
3416 && optimize_function_for_size_p (cfun)
3417 && standard_80387_constant_p (operands[1]))
3418 || GET_CODE (operands[1]) != CONST_DOUBLE
3419 || memory_operand (operands[0], DFmode))"
3421 switch (which_alternative)
3425 return output_387_reg_move (insn, operands);
3428 return standard_80387_constant_opcode (operands[1]);
3435 switch (get_attr_mode (insn))
3438 return "xorps\t%0, %0";
3440 return "xorpd\t%0, %0";
3442 return "pxor\t%0, %0";
3449 switch (get_attr_mode (insn))
3452 return "movaps\t{%1, %0|%0, %1}";
3454 return "movapd\t{%1, %0|%0, %1}";
3456 return "movdqa\t{%1, %0|%0, %1}";
3458 return "movq\t{%1, %0|%0, %1}";
3460 return "movsd\t{%1, %0|%0, %1}";
3462 return "movlpd\t{%1, %0|%0, %1}";
3464 return "movlps\t{%1, %0|%0, %1}";
3473 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
3475 (cond [(eq_attr "alternative" "0,1,2")
3477 (eq_attr "alternative" "3,4")
3480 /* For SSE1, we have many fewer alternatives. */
3481 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
3482 (cond [(eq_attr "alternative" "5,6")
3483 (const_string "V4SF")
3485 (const_string "V2SF"))
3487 /* xorps is one byte shorter. */
3488 (eq_attr "alternative" "5")
3489 (cond [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3491 (const_string "V4SF")
3492 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3496 (const_string "V2DF"))
3498 /* For architectures resolving dependencies on
3499 whole SSE registers use APD move to break dependency
3500 chains, otherwise use short move to avoid extra work.
3502 movaps encodes one byte shorter. */
3503 (eq_attr "alternative" "6")
3505 [(ne (symbol_ref "optimize_function_for_size_p (cfun)")
3507 (const_string "V4SF")
3508 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3510 (const_string "V2DF")
3512 (const_string "DF"))
3513 /* For architectures resolving dependencies on register
3514 parts we may avoid extra work to zero out upper part
3516 (eq_attr "alternative" "7")
3518 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3520 (const_string "V1DF")
3521 (const_string "DF"))
3523 (const_string "DF")))])
3526 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3527 (match_operand:DF 1 "general_operand" ""))]
3529 && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3530 && ! (ANY_FP_REG_P (operands[0]) ||
3531 (GET_CODE (operands[0]) == SUBREG
3532 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3533 && ! (ANY_FP_REG_P (operands[1]) ||
3534 (GET_CODE (operands[1]) == SUBREG
3535 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3537 "ix86_split_long_move (operands); DONE;")
3539 (define_insn "*swapdf"
3540 [(set (match_operand:DF 0 "fp_register_operand" "+f")
3541 (match_operand:DF 1 "fp_register_operand" "+f"))
3544 "reload_completed || TARGET_80387"
3546 if (STACK_TOP_P (operands[0]))
3551 [(set_attr "type" "fxch")
3552 (set_attr "mode" "DF")])
3554 (define_expand "movxf"
3555 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3556 (match_operand:XF 1 "general_operand" ""))]
3558 "ix86_expand_move (XFmode, operands); DONE;")
3560 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
3561 ;; Size of pushdf using integer instructions is 3+3*memory operand size
3562 ;; Pushing using integer instructions is longer except for constants
3563 ;; and direct memory references.
3564 ;; (assuming that any given constant is pushed only once, but this ought to be
3565 ;; handled elsewhere).
3567 (define_insn "*pushxf_nointeger"
3568 [(set (match_operand:XF 0 "push_operand" "=X,X,X")
3569 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
3570 "optimize_function_for_size_p (cfun)"
3572 /* This insn should be already split before reg-stack. */
3575 [(set_attr "type" "multi")
3576 (set_attr "unit" "i387,*,*")
3577 (set_attr "mode" "XF,SI,SI")])
3579 (define_insn "*pushxf_integer"
3580 [(set (match_operand:XF 0 "push_operand" "=<,<")
3581 (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
3582 "optimize_function_for_speed_p (cfun)"
3584 /* This insn should be already split before reg-stack. */
3587 [(set_attr "type" "multi")
3588 (set_attr "unit" "i387,*")
3589 (set_attr "mode" "XF,SI")])
3592 [(set (match_operand 0 "push_operand" "")
3593 (match_operand 1 "general_operand" ""))]
3595 && (GET_MODE (operands[0]) == XFmode
3596 || GET_MODE (operands[0]) == DFmode)
3597 && !ANY_FP_REG_P (operands[1])"
3599 "ix86_split_long_move (operands); DONE;")
3602 [(set (match_operand:XF 0 "push_operand" "")
3603 (match_operand:XF 1 "any_fp_register_operand" ""))]
3605 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3606 (set (mem:XF (reg:P SP_REG)) (match_dup 1))]
3607 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3609 ;; Do not use integer registers when optimizing for size
3610 (define_insn "*movxf_nointeger"
3611 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
3612 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
3613 "optimize_function_for_size_p (cfun)
3614 && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3615 && (reload_in_progress || reload_completed
3616 || standard_80387_constant_p (operands[1])
3617 || GET_CODE (operands[1]) != CONST_DOUBLE
3618 || memory_operand (operands[0], XFmode))"
3620 switch (which_alternative)
3624 return output_387_reg_move (insn, operands);
3627 return standard_80387_constant_opcode (operands[1]);
3635 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3636 (set_attr "mode" "XF,XF,XF,SI,SI")])
3638 (define_insn "*movxf_integer"
3639 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,r,o")
3640 (match_operand:XF 1 "general_operand" "fm,f,G,roF,Fr"))]
3641 "optimize_function_for_speed_p (cfun)
3642 && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3643 && (reload_in_progress || reload_completed
3644 || GET_CODE (operands[1]) != CONST_DOUBLE
3645 || memory_operand (operands[0], XFmode))"
3647 switch (which_alternative)
3651 return output_387_reg_move (insn, operands);
3654 return standard_80387_constant_opcode (operands[1]);
3663 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3664 (set_attr "mode" "XF,XF,XF,SI,SI")])
3666 (define_expand "movtf"
3667 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3668 (match_operand:TF 1 "nonimmediate_operand" ""))]
3671 ix86_expand_move (TFmode, operands);
3675 (define_insn "*movtf_internal"
3676 [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?r,?o")
3677 (match_operand:TF 1 "general_operand" "xm,x,C,roF,Fr"))]
3679 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3681 switch (which_alternative)
3685 if (get_attr_mode (insn) == MODE_V4SF)
3686 return "%vmovaps\t{%1, %0|%0, %1}";
3688 return "%vmovdqa\t{%1, %0|%0, %1}";
3690 if (get_attr_mode (insn) == MODE_V4SF)
3691 return "%vxorps\t%0, %d0";
3693 return "%vpxor\t%0, %d0";
3701 [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
3702 (set_attr "prefix" "maybe_vex,maybe_vex,maybe_vex,*,*")
3704 (cond [(eq_attr "alternative" "0,2")
3706 (ne (symbol_ref "optimize_function_for_size_p (cfun)")
3708 (const_string "V4SF")
3709 (const_string "TI"))
3710 (eq_attr "alternative" "1")
3712 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
3714 (ne (symbol_ref "optimize_function_for_size_p (cfun)")
3716 (const_string "V4SF")
3717 (const_string "TI"))]
3718 (const_string "DI")))])
3720 (define_insn "*pushtf_sse"
3721 [(set (match_operand:TF 0 "push_operand" "=<,<,<")
3722 (match_operand:TF 1 "general_no_elim_operand" "x,Fo,*r"))]
3725 /* This insn should be already split before reg-stack. */
3728 [(set_attr "type" "multi")
3729 (set_attr "unit" "sse,*,*")
3730 (set_attr "mode" "TF,SI,SI")])
3733 [(set (match_operand:TF 0 "push_operand" "")
3734 (match_operand:TF 1 "general_operand" ""))]
3735 "TARGET_SSE2 && reload_completed
3736 && !SSE_REG_P (operands[1])"
3738 "ix86_split_long_move (operands); DONE;")
3741 [(set (match_operand:TF 0 "push_operand" "")
3742 (match_operand:TF 1 "any_fp_register_operand" ""))]
3744 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -16)))
3745 (set (mem:TF (reg:P SP_REG)) (match_dup 1))]
3749 [(set (match_operand 0 "nonimmediate_operand" "")
3750 (match_operand 1 "general_operand" ""))]
3752 && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3753 && GET_MODE (operands[0]) == XFmode
3754 && ! (ANY_FP_REG_P (operands[0]) ||
3755 (GET_CODE (operands[0]) == SUBREG
3756 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3757 && ! (ANY_FP_REG_P (operands[1]) ||
3758 (GET_CODE (operands[1]) == SUBREG
3759 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3761 "ix86_split_long_move (operands); DONE;")
3764 [(set (match_operand 0 "register_operand" "")
3765 (match_operand 1 "memory_operand" ""))]
3767 && MEM_P (operands[1])
3768 && (GET_MODE (operands[0]) == TFmode
3769 || GET_MODE (operands[0]) == XFmode
3770 || GET_MODE (operands[0]) == SFmode
3771 || GET_MODE (operands[0]) == DFmode)
3772 && (operands[2] = find_constant_src (insn))"
3773 [(set (match_dup 0) (match_dup 2))]
3775 rtx c = operands[2];
3776 rtx r = operands[0];
3778 if (GET_CODE (r) == SUBREG)
3783 if (!standard_sse_constant_p (c))
3786 else if (FP_REG_P (r))
3788 if (!standard_80387_constant_p (c))
3791 else if (MMX_REG_P (r))
3796 [(set (match_operand 0 "register_operand" "")
3797 (float_extend (match_operand 1 "memory_operand" "")))]
3799 && MEM_P (operands[1])
3800 && (GET_MODE (operands[0]) == TFmode
3801 || GET_MODE (operands[0]) == XFmode
3802 || GET_MODE (operands[0]) == SFmode
3803 || GET_MODE (operands[0]) == DFmode)
3804 && (operands[2] = find_constant_src (insn))"
3805 [(set (match_dup 0) (match_dup 2))]
3807 rtx c = operands[2];
3808 rtx r = operands[0];
3810 if (GET_CODE (r) == SUBREG)
3815 if (!standard_sse_constant_p (c))
3818 else if (FP_REG_P (r))
3820 if (!standard_80387_constant_p (c))
3823 else if (MMX_REG_P (r))
3827 (define_insn "swapxf"
3828 [(set (match_operand:XF 0 "register_operand" "+f")
3829 (match_operand:XF 1 "register_operand" "+f"))
3834 if (STACK_TOP_P (operands[0]))
3839 [(set_attr "type" "fxch")
3840 (set_attr "mode" "XF")])
3842 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3844 [(set (match_operand:X87MODEF 0 "register_operand" "")
3845 (match_operand:X87MODEF 1 "immediate_operand" ""))]
3846 "reload_completed && FP_REGNO_P (REGNO (operands[0]))
3847 && (standard_80387_constant_p (operands[1]) == 8
3848 || standard_80387_constant_p (operands[1]) == 9)"
3849 [(set (match_dup 0)(match_dup 1))
3851 (neg:X87MODEF (match_dup 0)))]
3855 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3856 if (real_isnegzero (&r))
3857 operands[1] = CONST0_RTX (<MODE>mode);
3859 operands[1] = CONST1_RTX (<MODE>mode);
3863 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3864 (match_operand:TF 1 "general_operand" ""))]
3866 && !(SSE_REG_P (operands[0]) || SSE_REG_P (operands[1]))"
3868 "ix86_split_long_move (operands); DONE;")
3870 ;; Zero extension instructions
3872 (define_expand "zero_extendhisi2"
3873 [(set (match_operand:SI 0 "register_operand" "")
3874 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3877 if (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3879 operands[1] = force_reg (HImode, operands[1]);
3880 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3885 (define_insn "zero_extendhisi2_and"
3886 [(set (match_operand:SI 0 "register_operand" "=r")
3887 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3888 (clobber (reg:CC FLAGS_REG))]
3889 "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3891 [(set_attr "type" "alu1")
3892 (set_attr "mode" "SI")])
3895 [(set (match_operand:SI 0 "register_operand" "")
3896 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
3897 (clobber (reg:CC FLAGS_REG))]
3898 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND
3899 && optimize_function_for_speed_p (cfun)"
3900 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3901 (clobber (reg:CC FLAGS_REG))])]
3904 (define_insn "*zero_extendhisi2_movzwl"
3905 [(set (match_operand:SI 0 "register_operand" "=r")
3906 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3907 "!TARGET_ZERO_EXTEND_WITH_AND
3908 || optimize_function_for_size_p (cfun)"
3909 "movz{wl|x}\t{%1, %0|%0, %1}"
3910 [(set_attr "type" "imovx")
3911 (set_attr "mode" "SI")])
3913 (define_expand "zero_extendqihi2"
3915 [(set (match_operand:HI 0 "register_operand" "")
3916 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3917 (clobber (reg:CC FLAGS_REG))])]
3921 (define_insn "*zero_extendqihi2_and"
3922 [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3923 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3924 (clobber (reg:CC FLAGS_REG))]
3925 "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3927 [(set_attr "type" "alu1")
3928 (set_attr "mode" "HI")])
3930 (define_insn "*zero_extendqihi2_movzbw_and"
3931 [(set (match_operand:HI 0 "register_operand" "=r,r")
3932 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3933 (clobber (reg:CC FLAGS_REG))]
3934 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun)"
3936 [(set_attr "type" "imovx,alu1")
3937 (set_attr "mode" "HI")])
3939 ; zero extend to SImode here to avoid partial register stalls
3940 (define_insn "*zero_extendqihi2_movzbl"
3941 [(set (match_operand:HI 0 "register_operand" "=r")
3942 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3943 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
3944 && reload_completed"
3945 "movz{bl|x}\t{%1, %k0|%k0, %1}"
3946 [(set_attr "type" "imovx")
3947 (set_attr "mode" "SI")])
3949 ;; For the movzbw case strip only the clobber
3951 [(set (match_operand:HI 0 "register_operand" "")
3952 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3953 (clobber (reg:CC FLAGS_REG))]
3955 && (!TARGET_ZERO_EXTEND_WITH_AND
3956 || optimize_function_for_size_p (cfun))
3957 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3958 [(set (match_operand:HI 0 "register_operand" "")
3959 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3961 ;; When source and destination does not overlap, clear destination
3962 ;; first and then do the movb
3964 [(set (match_operand:HI 0 "register_operand" "")
3965 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3966 (clobber (reg:CC FLAGS_REG))]
3968 && ANY_QI_REG_P (operands[0])
3969 && (TARGET_ZERO_EXTEND_WITH_AND
3970 && optimize_function_for_speed_p (cfun))
3971 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3972 [(set (match_dup 0) (const_int 0))
3973 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3974 "operands[2] = gen_lowpart (QImode, operands[0]);")
3976 ;; Rest is handled by single and.
3978 [(set (match_operand:HI 0 "register_operand" "")
3979 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3980 (clobber (reg:CC FLAGS_REG))]
3982 && true_regnum (operands[0]) == true_regnum (operands[1])"
3983 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3984 (clobber (reg:CC FLAGS_REG))])]
3987 (define_expand "zero_extendqisi2"
3989 [(set (match_operand:SI 0 "register_operand" "")
3990 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3991 (clobber (reg:CC FLAGS_REG))])]
3995 (define_insn "*zero_extendqisi2_and"
3996 [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3997 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3998 (clobber (reg:CC FLAGS_REG))]
3999 "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
4001 [(set_attr "type" "alu1")
4002 (set_attr "mode" "SI")])
4004 (define_insn "*zero_extendqisi2_movzbw_and"
4005 [(set (match_operand:SI 0 "register_operand" "=r,r")
4006 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
4007 (clobber (reg:CC FLAGS_REG))]
4008 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun)"
4010 [(set_attr "type" "imovx,alu1")
4011 (set_attr "mode" "SI")])
4013 (define_insn "*zero_extendqisi2_movzbw"
4014 [(set (match_operand:SI 0 "register_operand" "=r")
4015 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
4016 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
4017 && reload_completed"
4018 "movz{bl|x}\t{%1, %0|%0, %1}"
4019 [(set_attr "type" "imovx")
4020 (set_attr "mode" "SI")])
4022 ;; For the movzbl case strip only the clobber
4024 [(set (match_operand:SI 0 "register_operand" "")
4025 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
4026 (clobber (reg:CC FLAGS_REG))]
4028 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
4029 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
4031 (zero_extend:SI (match_dup 1)))])
4033 ;; When source and destination does not overlap, clear destination
4034 ;; first and then do the movb
4036 [(set (match_operand:SI 0 "register_operand" "")
4037 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
4038 (clobber (reg:CC FLAGS_REG))]
4040 && ANY_QI_REG_P (operands[0])
4041 && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
4042 && (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
4043 && !reg_overlap_mentioned_p (operands[0], operands[1])"
4044 [(set (match_dup 0) (const_int 0))
4045 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4046 "operands[2] = gen_lowpart (QImode, operands[0]);")
4048 ;; Rest is handled by single and.
4050 [(set (match_operand:SI 0 "register_operand" "")
4051 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
4052 (clobber (reg:CC FLAGS_REG))]
4054 && true_regnum (operands[0]) == true_regnum (operands[1])"
4055 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
4056 (clobber (reg:CC FLAGS_REG))])]
4059 ;; %%% Kill me once multi-word ops are sane.
4060 (define_expand "zero_extendsidi2"
4061 [(set (match_operand:DI 0 "register_operand" "")
4062 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4067 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
4072 (define_insn "zero_extendsidi2_32"
4073 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*Y2")
4075 (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r ,m ,r ,m")))
4076 (clobber (reg:CC FLAGS_REG))]
4082 movd\t{%1, %0|%0, %1}
4083 movd\t{%1, %0|%0, %1}
4084 %vmovd\t{%1, %0|%0, %1}
4085 %vmovd\t{%1, %0|%0, %1}"
4086 [(set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")
4087 (set_attr "prefix" "*,*,*,orig,orig,maybe_vex,maybe_vex")
4088 (set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")])
4090 (define_insn "zero_extendsidi2_rex64"
4091 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*Ym,?*y,?*Yi,*Y2")
4093 (match_operand:SI 1 "nonimmediate_operand" "rm,0,r ,m ,r ,m")))]
4096 mov\t{%k1, %k0|%k0, %k1}
4098 movd\t{%1, %0|%0, %1}
4099 movd\t{%1, %0|%0, %1}
4100 %vmovd\t{%1, %0|%0, %1}
4101 %vmovd\t{%1, %0|%0, %1}"
4102 [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
4103 (set_attr "prefix" "orig,*,orig,orig,maybe_vex,maybe_vex")
4104 (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
4107 [(set (match_operand:DI 0 "memory_operand" "")
4108 (zero_extend:DI (match_dup 0)))]
4110 [(set (match_dup 4) (const_int 0))]
4111 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
4114 [(set (match_operand:DI 0 "register_operand" "")
4115 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
4116 (clobber (reg:CC FLAGS_REG))]
4117 "!TARGET_64BIT && reload_completed
4118 && true_regnum (operands[0]) == true_regnum (operands[1])"
4119 [(set (match_dup 4) (const_int 0))]
4120 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
4123 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4124 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
4125 (clobber (reg:CC FLAGS_REG))]
4126 "!TARGET_64BIT && reload_completed
4127 && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
4128 [(set (match_dup 3) (match_dup 1))
4129 (set (match_dup 4) (const_int 0))]
4130 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
4132 (define_insn "zero_extendhidi2"
4133 [(set (match_operand:DI 0 "register_operand" "=r")
4134 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
4136 "movz{wl|x}\t{%1, %k0|%k0, %1}"
4137 [(set_attr "type" "imovx")
4138 (set_attr "mode" "DI")])
4140 (define_insn "zero_extendqidi2"
4141 [(set (match_operand:DI 0 "register_operand" "=r")
4142 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))]
4144 "movz{bl|x}\t{%1, %k0|%k0, %1}"
4145 [(set_attr "type" "imovx")
4146 (set_attr "mode" "DI")])
4148 ;; Sign extension instructions
4150 (define_expand "extendsidi2"
4151 [(parallel [(set (match_operand:DI 0 "register_operand" "")
4152 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
4153 (clobber (reg:CC FLAGS_REG))
4154 (clobber (match_scratch:SI 2 ""))])]
4159 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
4164 (define_insn "*extendsidi2_1"
4165 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
4166 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
4167 (clobber (reg:CC FLAGS_REG))
4168 (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
4172 (define_insn "extendsidi2_rex64"
4173 [(set (match_operand:DI 0 "register_operand" "=*a,r")
4174 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
4178 movs{lq|x}\t{%1,%0|%0, %1}"
4179 [(set_attr "type" "imovx")
4180 (set_attr "mode" "DI")
4181 (set_attr "prefix_0f" "0")
4182 (set_attr "modrm" "0,1")])
4184 (define_insn "extendhidi2"
4185 [(set (match_operand:DI 0 "register_operand" "=r")
4186 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
4188 "movs{wq|x}\t{%1,%0|%0, %1}"
4189 [(set_attr "type" "imovx")
4190 (set_attr "mode" "DI")])
4192 (define_insn "extendqidi2"
4193 [(set (match_operand:DI 0 "register_operand" "=r")
4194 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
4196 "movs{bq|x}\t{%1,%0|%0, %1}"
4197 [(set_attr "type" "imovx")
4198 (set_attr "mode" "DI")])
4200 ;; Extend to memory case when source register does die.
4202 [(set (match_operand:DI 0 "memory_operand" "")
4203 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
4204 (clobber (reg:CC FLAGS_REG))
4205 (clobber (match_operand:SI 2 "register_operand" ""))]
4207 && dead_or_set_p (insn, operands[1])
4208 && !reg_mentioned_p (operands[1], operands[0]))"
4209 [(set (match_dup 3) (match_dup 1))
4210 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
4211 (clobber (reg:CC FLAGS_REG))])
4212 (set (match_dup 4) (match_dup 1))]
4213 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
4215 ;; Extend to memory case when source register does not die.
4217 [(set (match_operand:DI 0 "memory_operand" "")
4218 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
4219 (clobber (reg:CC FLAGS_REG))
4220 (clobber (match_operand:SI 2 "register_operand" ""))]
4224 split_di (&operands[0], 1, &operands[3], &operands[4]);
4226 emit_move_insn (operands[3], operands[1]);
4228 /* Generate a cltd if possible and doing so it profitable. */
4229 if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
4230 && true_regnum (operands[1]) == AX_REG
4231 && true_regnum (operands[2]) == DX_REG)
4233 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
4237 emit_move_insn (operands[2], operands[1]);
4238 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
4240 emit_move_insn (operands[4], operands[2]);
4244 ;; Extend to register case. Optimize case where source and destination
4245 ;; registers match and cases where we can use cltd.
4247 [(set (match_operand:DI 0 "register_operand" "")
4248 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
4249 (clobber (reg:CC FLAGS_REG))
4250 (clobber (match_scratch:SI 2 ""))]
4254 split_di (&operands[0], 1, &operands[3], &operands[4]);
4256 if (true_regnum (operands[3]) != true_regnum (operands[1]))
4257 emit_move_insn (operands[3], operands[1]);
4259 /* Generate a cltd if possible and doing so it profitable. */
4260 if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
4261 && true_regnum (operands[3]) == AX_REG)
4263 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
4267 if (true_regnum (operands[4]) != true_regnum (operands[1]))
4268 emit_move_insn (operands[4], operands[1]);
4270 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
4274 (define_insn "extendhisi2"
4275 [(set (match_operand:SI 0 "register_operand" "=*a,r")
4276 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
4279 switch (get_attr_prefix_0f (insn))
4282 return "{cwtl|cwde}";
4284 return "movs{wl|x}\t{%1,%0|%0, %1}";
4287 [(set_attr "type" "imovx")
4288 (set_attr "mode" "SI")
4289 (set (attr "prefix_0f")
4290 ;; movsx is short decodable while cwtl is vector decoded.
4291 (if_then_else (and (eq_attr "cpu" "!k6")
4292 (eq_attr "alternative" "0"))
4294 (const_string "1")))
4296 (if_then_else (eq_attr "prefix_0f" "0")
4298 (const_string "1")))])
4300 (define_insn "*extendhisi2_zext"
4301 [(set (match_operand:DI 0 "register_operand" "=*a,r")
4303 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
4306 switch (get_attr_prefix_0f (insn))
4309 return "{cwtl|cwde}";
4311 return "movs{wl|x}\t{%1,%k0|%k0, %1}";
4314 [(set_attr "type" "imovx")
4315 (set_attr "mode" "SI")
4316 (set (attr "prefix_0f")
4317 ;; movsx is short decodable while cwtl is vector decoded.
4318 (if_then_else (and (eq_attr "cpu" "!k6")
4319 (eq_attr "alternative" "0"))
4321 (const_string "1")))
4323 (if_then_else (eq_attr "prefix_0f" "0")
4325 (const_string "1")))])
4327 (define_insn "extendqihi2"
4328 [(set (match_operand:HI 0 "register_operand" "=*a,r")
4329 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
4332 switch (get_attr_prefix_0f (insn))
4335 return "{cbtw|cbw}";
4337 return "movs{bw|x}\t{%1,%0|%0, %1}";
4340 [(set_attr "type" "imovx")
4341 (set_attr "mode" "HI")
4342 (set (attr "prefix_0f")
4343 ;; movsx is short decodable while cwtl is vector decoded.
4344 (if_then_else (and (eq_attr "cpu" "!k6")
4345 (eq_attr "alternative" "0"))
4347 (const_string "1")))
4349 (if_then_else (eq_attr "prefix_0f" "0")
4351 (const_string "1")))])
4353 (define_insn "extendqisi2"
4354 [(set (match_operand:SI 0 "register_operand" "=r")
4355 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
4357 "movs{bl|x}\t{%1,%0|%0, %1}"
4358 [(set_attr "type" "imovx")
4359 (set_attr "mode" "SI")])
4361 (define_insn "*extendqisi2_zext"
4362 [(set (match_operand:DI 0 "register_operand" "=r")
4364 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
4366 "movs{bl|x}\t{%1,%k0|%k0, %1}"
4367 [(set_attr "type" "imovx")
4368 (set_attr "mode" "SI")])
4370 ;; Conversions between float and double.
4372 ;; These are all no-ops in the model used for the 80387. So just
4375 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
4376 (define_insn "*dummy_extendsfdf2"
4377 [(set (match_operand:DF 0 "push_operand" "=<")
4378 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY2")))]
4383 [(set (match_operand:DF 0 "push_operand" "")
4384 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
4386 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
4387 (set (mem:DF (reg:P SP_REG)) (float_extend:DF (match_dup 1)))])
4389 (define_insn "*dummy_extendsfxf2"
4390 [(set (match_operand:XF 0 "push_operand" "=<")
4391 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
4396 [(set (match_operand:XF 0 "push_operand" "")
4397 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
4399 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
4400 (set (mem:XF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
4401 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
4404 [(set (match_operand:XF 0 "push_operand" "")
4405 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
4407 [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
4408 (set (mem:DF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
4409 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
4411 (define_expand "extendsfdf2"
4412 [(set (match_operand:DF 0 "nonimmediate_operand" "")
4413 (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
4414 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4416 /* ??? Needed for compress_float_constant since all fp constants
4417 are LEGITIMATE_CONSTANT_P. */
4418 if (GET_CODE (operands[1]) == CONST_DOUBLE)
4420 if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
4421 && standard_80387_constant_p (operands[1]) > 0)
4423 operands[1] = simplify_const_unary_operation
4424 (FLOAT_EXTEND, DFmode, operands[1], SFmode);
4425 emit_move_insn_1 (operands[0], operands[1]);
4428 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
4432 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
4434 unpcklps xmm2,xmm2 ; packed conversion might crash on signaling NaNs
4436 We do the conversion post reload to avoid producing of 128bit spills
4437 that might lead to ICE on 32bit target. The sequence unlikely combine
4440 [(set (match_operand:DF 0 "register_operand" "")
4442 (match_operand:SF 1 "nonimmediate_operand" "")))]
4443 "TARGET_USE_VECTOR_FP_CONVERTS
4444 && optimize_insn_for_speed_p ()
4445 && reload_completed && SSE_REG_P (operands[0])"
4450 (parallel [(const_int 0) (const_int 1)]))))]
4452 operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
4453 operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
4454 /* Use movss for loading from memory, unpcklps reg, reg for registers.
4455 Try to avoid move when unpacking can be done in source. */
4456 if (REG_P (operands[1]))
4458 /* If it is unsafe to overwrite upper half of source, we need
4459 to move to destination and unpack there. */
4460 if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4461 || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
4462 && true_regnum (operands[0]) != true_regnum (operands[1]))
4464 rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
4465 emit_move_insn (tmp, operands[1]);
4468 operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4469 emit_insn (gen_sse_unpcklps (operands[3], operands[3], operands[3]));
4472 emit_insn (gen_vec_setv4sf_0 (operands[3],
4473 CONST0_RTX (V4SFmode), operands[1]));
4476 (define_insn "*extendsfdf2_mixed"
4477 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
4479 (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
4480 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4482 switch (which_alternative)
4486 return output_387_reg_move (insn, operands);
4489 return "%vcvtss2sd\t{%1, %d0|%d0, %1}";
4495 [(set_attr "type" "fmov,fmov,ssecvt")
4496 (set_attr "prefix" "orig,orig,maybe_vex")
4497 (set_attr "mode" "SF,XF,DF")])
4499 (define_insn "*extendsfdf2_sse"
4500 [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
4501 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
4502 "TARGET_SSE2 && TARGET_SSE_MATH"
4503 "%vcvtss2sd\t{%1, %d0|%d0, %1}"
4504 [(set_attr "type" "ssecvt")
4505 (set_attr "prefix" "maybe_vex")
4506 (set_attr "mode" "DF")])
4508 (define_insn "*extendsfdf2_i387"
4509 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
4510 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
4512 "* return output_387_reg_move (insn, operands);"
4513 [(set_attr "type" "fmov")
4514 (set_attr "mode" "SF,XF")])
4516 (define_expand "extend<mode>xf2"
4517 [(set (match_operand:XF 0 "nonimmediate_operand" "")
4518 (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
4521 /* ??? Needed for compress_float_constant since all fp constants
4522 are LEGITIMATE_CONSTANT_P. */
4523 if (GET_CODE (operands[1]) == CONST_DOUBLE)
4525 if (standard_80387_constant_p (operands[1]) > 0)
4527 operands[1] = simplify_const_unary_operation
4528 (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
4529 emit_move_insn_1 (operands[0], operands[1]);
4532 operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
4536 (define_insn "*extend<mode>xf2_i387"
4537 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
4539 (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
4541 "* return output_387_reg_move (insn, operands);"
4542 [(set_attr "type" "fmov")
4543 (set_attr "mode" "<MODE>,XF")])
4545 ;; %%% This seems bad bad news.
4546 ;; This cannot output into an f-reg because there is no way to be sure
4547 ;; of truncating in that case. Otherwise this is just like a simple move
4548 ;; insn. So we pretend we can output to a reg in order to get better
4549 ;; register preferencing, but we really use a stack slot.
4551 ;; Conversion from DFmode to SFmode.
4553 (define_expand "truncdfsf2"
4554 [(set (match_operand:SF 0 "nonimmediate_operand" "")
4556 (match_operand:DF 1 "nonimmediate_operand" "")))]
4557 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4559 if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
4561 else if (flag_unsafe_math_optimizations)
4565 enum ix86_stack_slot slot = (virtuals_instantiated
4568 rtx temp = assign_386_stack_local (SFmode, slot);
4569 emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
4574 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
4576 unpcklpd xmm2,xmm2 ; packed conversion might crash on signaling NaNs
4578 We do the conversion post reload to avoid producing of 128bit spills
4579 that might lead to ICE on 32bit target. The sequence unlikely combine
4582 [(set (match_operand:SF 0 "register_operand" "")
4584 (match_operand:DF 1 "nonimmediate_operand" "")))]
4585 "TARGET_USE_VECTOR_FP_CONVERTS
4586 && optimize_insn_for_speed_p ()
4587 && reload_completed && SSE_REG_P (operands[0])"
4590 (float_truncate:V2SF
4594 operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4595 operands[3] = CONST0_RTX (V2SFmode);
4596 operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
4597 /* Use movsd for loading from memory, unpcklpd for registers.
4598 Try to avoid move when unpacking can be done in source, or SSE3
4599 movddup is available. */
4600 if (REG_P (operands[1]))
4603 && true_regnum (operands[0]) != true_regnum (operands[1])
4604 && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4605 || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
4607 rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
4608 emit_move_insn (tmp, operands[1]);
4611 else if (!TARGET_SSE3)
4612 operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4613 emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4616 emit_insn (gen_sse2_loadlpd (operands[4],
4617 CONST0_RTX (V2DFmode), operands[1]));
4620 (define_expand "truncdfsf2_with_temp"
4621 [(parallel [(set (match_operand:SF 0 "" "")
4622 (float_truncate:SF (match_operand:DF 1 "" "")))
4623 (clobber (match_operand:SF 2 "" ""))])]
4626 (define_insn "*truncdfsf_fast_mixed"
4627 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm,x")
4629 (match_operand:DF 1 "nonimmediate_operand" "f ,xm")))]
4630 "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4632 switch (which_alternative)
4635 return output_387_reg_move (insn, operands);
4637 return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4642 [(set_attr "type" "fmov,ssecvt")
4643 (set_attr "prefix" "orig,maybe_vex")
4644 (set_attr "mode" "SF")])
4646 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4647 ;; because nothing we do here is unsafe.
4648 (define_insn "*truncdfsf_fast_sse"
4649 [(set (match_operand:SF 0 "nonimmediate_operand" "=x")
4651 (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4652 "TARGET_SSE2 && TARGET_SSE_MATH"
4653 "%vcvtsd2ss\t{%1, %d0|%d0, %1}"
4654 [(set_attr "type" "ssecvt")
4655 (set_attr "prefix" "maybe_vex")
4656 (set_attr "mode" "SF")])
4658 (define_insn "*truncdfsf_fast_i387"
4659 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm")
4661 (match_operand:DF 1 "nonimmediate_operand" "f")))]
4662 "TARGET_80387 && flag_unsafe_math_optimizations"
4663 "* return output_387_reg_move (insn, operands);"
4664 [(set_attr "type" "fmov")
4665 (set_attr "mode" "SF")])
4667 (define_insn "*truncdfsf_mixed"
4668 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,Y2 ,?f,?x,?*r")
4670 (match_operand:DF 1 "nonimmediate_operand" "f ,Y2m,f ,f ,f")))
4671 (clobber (match_operand:SF 2 "memory_operand" "=X,X ,m ,m ,m"))]
4672 "TARGET_MIX_SSE_I387"
4674 switch (which_alternative)
4677 return output_387_reg_move (insn, operands);
4679 return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4685 [(set_attr "type" "fmov,ssecvt,multi,multi,multi")
4686 (set_attr "unit" "*,*,i387,i387,i387")
4687 (set_attr "prefix" "orig,maybe_vex,orig,orig,orig")
4688 (set_attr "mode" "SF")])
4690 (define_insn "*truncdfsf_i387"
4691 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4693 (match_operand:DF 1 "nonimmediate_operand" "f ,f ,f ,f")))
4694 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,m ,m"))]
4697 switch (which_alternative)
4700 return output_387_reg_move (insn, operands);
4706 [(set_attr "type" "fmov,multi,multi,multi")
4707 (set_attr "unit" "*,i387,i387,i387")
4708 (set_attr "mode" "SF")])
4710 (define_insn "*truncdfsf2_i387_1"
4711 [(set (match_operand:SF 0 "memory_operand" "=m")
4713 (match_operand:DF 1 "register_operand" "f")))]
4715 && !(TARGET_SSE2 && TARGET_SSE_MATH)
4716 && !TARGET_MIX_SSE_I387"
4717 "* return output_387_reg_move (insn, operands);"
4718 [(set_attr "type" "fmov")
4719 (set_attr "mode" "SF")])
4722 [(set (match_operand:SF 0 "register_operand" "")
4724 (match_operand:DF 1 "fp_register_operand" "")))
4725 (clobber (match_operand 2 "" ""))]
4727 [(set (match_dup 2) (match_dup 1))
4728 (set (match_dup 0) (match_dup 2))]
4730 operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
4733 ;; Conversion from XFmode to {SF,DF}mode
4735 (define_expand "truncxf<mode>2"
4736 [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4737 (float_truncate:MODEF
4738 (match_operand:XF 1 "register_operand" "")))
4739 (clobber (match_dup 2))])]
4742 if (flag_unsafe_math_optimizations)
4744 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4745 emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4746 if (reg != operands[0])
4747 emit_move_insn (operands[0], reg);
4752 enum ix86_stack_slot slot = (virtuals_instantiated
4755 operands[2] = assign_386_stack_local (<MODE>mode, slot);
4759 (define_insn "*truncxfsf2_mixed"
4760 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4762 (match_operand:XF 1 "register_operand" "f ,f ,f ,f")))
4763 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,m ,m"))]
4766 gcc_assert (!which_alternative);
4767 return output_387_reg_move (insn, operands);
4769 [(set_attr "type" "fmov,multi,multi,multi")
4770 (set_attr "unit" "*,i387,i387,i387")
4771 (set_attr "mode" "SF")])
4773 (define_insn "*truncxfdf2_mixed"
4774 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?Y2,?*r")
4776 (match_operand:XF 1 "register_operand" "f ,f ,f ,f")))
4777 (clobber (match_operand:DF 2 "memory_operand" "=X,m ,m ,m"))]
4780 gcc_assert (!which_alternative);
4781 return output_387_reg_move (insn, operands);
4783 [(set_attr "type" "fmov,multi,multi,multi")
4784 (set_attr "unit" "*,i387,i387,i387")
4785 (set_attr "mode" "DF")])
4787 (define_insn "truncxf<mode>2_i387_noop"
4788 [(set (match_operand:MODEF 0 "register_operand" "=f")
4789 (float_truncate:MODEF
4790 (match_operand:XF 1 "register_operand" "f")))]
4791 "TARGET_80387 && flag_unsafe_math_optimizations"
4792 "* return output_387_reg_move (insn, operands);"
4793 [(set_attr "type" "fmov")
4794 (set_attr "mode" "<MODE>")])
4796 (define_insn "*truncxf<mode>2_i387"
4797 [(set (match_operand:MODEF 0 "memory_operand" "=m")
4798 (float_truncate:MODEF
4799 (match_operand:XF 1 "register_operand" "f")))]
4801 "* return output_387_reg_move (insn, operands);"
4802 [(set_attr "type" "fmov")
4803 (set_attr "mode" "<MODE>")])
4806 [(set (match_operand:MODEF 0 "register_operand" "")
4807 (float_truncate:MODEF
4808 (match_operand:XF 1 "register_operand" "")))
4809 (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4810 "TARGET_80387 && reload_completed"
4811 [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4812 (set (match_dup 0) (match_dup 2))]
4816 [(set (match_operand:MODEF 0 "memory_operand" "")
4817 (float_truncate:MODEF
4818 (match_operand:XF 1 "register_operand" "")))
4819 (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4821 [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))]
4824 ;; Signed conversion to DImode.
4826 (define_expand "fix_truncxfdi2"
4827 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4828 (fix:DI (match_operand:XF 1 "register_operand" "")))
4829 (clobber (reg:CC FLAGS_REG))])]
4834 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4839 (define_expand "fix_trunc<mode>di2"
4840 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4841 (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4842 (clobber (reg:CC FLAGS_REG))])]
4843 "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4846 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4848 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4851 if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4853 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4854 emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4855 if (out != operands[0])
4856 emit_move_insn (operands[0], out);
4861 ;; Signed conversion to SImode.
4863 (define_expand "fix_truncxfsi2"
4864 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4865 (fix:SI (match_operand:XF 1 "register_operand" "")))
4866 (clobber (reg:CC FLAGS_REG))])]
4871 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4876 (define_expand "fix_trunc<mode>si2"
4877 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4878 (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4879 (clobber (reg:CC FLAGS_REG))])]
4880 "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4883 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4885 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4888 if (SSE_FLOAT_MODE_P (<MODE>mode))
4890 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4891 emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4892 if (out != operands[0])
4893 emit_move_insn (operands[0], out);
4898 ;; Signed conversion to HImode.
4900 (define_expand "fix_trunc<mode>hi2"
4901 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4902 (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4903 (clobber (reg:CC FLAGS_REG))])]
4905 && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4909 emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4914 ;; Unsigned conversion to SImode.
4916 (define_expand "fixuns_trunc<mode>si2"
4918 [(set (match_operand:SI 0 "register_operand" "")
4920 (match_operand:MODEF 1 "nonimmediate_operand" "")))
4922 (clobber (match_scratch:<ssevecmode> 3 ""))
4923 (clobber (match_scratch:<ssevecmode> 4 ""))])]
4924 "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4926 enum machine_mode mode = <MODE>mode;
4927 enum machine_mode vecmode = <ssevecmode>mode;
4928 REAL_VALUE_TYPE TWO31r;
4931 if (optimize_insn_for_size_p ())
4934 real_ldexp (&TWO31r, &dconst1, 31);
4935 two31 = const_double_from_real_value (TWO31r, mode);
4936 two31 = ix86_build_const_vector (mode, true, two31);
4937 operands[2] = force_reg (vecmode, two31);
4940 (define_insn_and_split "*fixuns_trunc<mode>_1"
4941 [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4943 (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4944 (use (match_operand:<ssevecmode> 4 "nonimmediate_operand" "m,x"))
4945 (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4946 (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4947 "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
4948 && optimize_function_for_speed_p (cfun)"
4950 "&& reload_completed"
4953 ix86_split_convert_uns_si_sse (operands);
4957 ;; Unsigned conversion to HImode.
4958 ;; Without these patterns, we'll try the unsigned SI conversion which
4959 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4961 (define_expand "fixuns_trunc<mode>hi2"
4963 (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4964 (set (match_operand:HI 0 "nonimmediate_operand" "")
4965 (subreg:HI (match_dup 2) 0))]
4966 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4967 "operands[2] = gen_reg_rtx (SImode);")
4969 ;; When SSE is available, it is always faster to use it!
4970 (define_insn "fix_trunc<mode>di_sse"
4971 [(set (match_operand:DI 0 "register_operand" "=r,r")
4972 (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4973 "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4974 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4975 "%vcvtts<ssemodefsuffix>2si{q}\t{%1, %0|%0, %1}"
4976 [(set_attr "type" "sseicvt")
4977 (set_attr "prefix" "maybe_vex")
4978 (set_attr "mode" "<MODE>")
4979 (set_attr "athlon_decode" "double,vector")
4980 (set_attr "amdfam10_decode" "double,double")])
4982 (define_insn "fix_trunc<mode>si_sse"
4983 [(set (match_operand:SI 0 "register_operand" "=r,r")
4984 (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4985 "SSE_FLOAT_MODE_P (<MODE>mode)
4986 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4987 "%vcvtts<ssemodefsuffix>2si\t{%1, %0|%0, %1}"
4988 [(set_attr "type" "sseicvt")
4989 (set_attr "prefix" "maybe_vex")
4990 (set_attr "mode" "<MODE>")
4991 (set_attr "athlon_decode" "double,vector")
4992 (set_attr "amdfam10_decode" "double,double")])
4994 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4996 [(set (match_operand:MODEF 0 "register_operand" "")
4997 (match_operand:MODEF 1 "memory_operand" ""))
4998 (set (match_operand:SSEMODEI24 2 "register_operand" "")
4999 (fix:SSEMODEI24 (match_dup 0)))]
5000 "TARGET_SHORTEN_X87_SSE
5001 && peep2_reg_dead_p (2, operands[0])"
5002 [(set (match_dup 2) (fix:SSEMODEI24 (match_dup 1)))]
5005 ;; Avoid vector decoded forms of the instruction.
5007 [(match_scratch:DF 2 "Y2")
5008 (set (match_operand:SSEMODEI24 0 "register_operand" "")
5009 (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
5010 "TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
5011 [(set (match_dup 2) (match_dup 1))
5012 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
5016 [(match_scratch:SF 2 "x")
5017 (set (match_operand:SSEMODEI24 0 "register_operand" "")
5018 (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
5019 "TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
5020 [(set (match_dup 2) (match_dup 1))
5021 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
5024 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
5025 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
5026 (fix:X87MODEI (match_operand 1 "register_operand" "")))]
5027 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5029 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
5030 && (TARGET_64BIT || <MODE>mode != DImode))
5032 && !(reload_completed || reload_in_progress)"
5037 if (memory_operand (operands[0], VOIDmode))
5038 emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
5041 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
5042 emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
5048 [(set_attr "type" "fisttp")
5049 (set_attr "mode" "<MODE>")])
5051 (define_insn "fix_trunc<mode>_i387_fisttp"
5052 [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
5053 (fix:X87MODEI (match_operand 1 "register_operand" "f")))
5054 (clobber (match_scratch:XF 2 "=&1f"))]
5055 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5057 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
5058 && (TARGET_64BIT || <MODE>mode != DImode))
5059 && TARGET_SSE_MATH)"
5060 "* return output_fix_trunc (insn, operands, 1);"
5061 [(set_attr "type" "fisttp")
5062 (set_attr "mode" "<MODE>")])
5064 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
5065 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
5066 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
5067 (clobber (match_operand:X87MODEI 2 "memory_operand" "=X,m"))
5068 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
5069 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5071 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
5072 && (TARGET_64BIT || <MODE>mode != DImode))
5073 && TARGET_SSE_MATH)"
5075 [(set_attr "type" "fisttp")
5076 (set_attr "mode" "<MODE>")])
5079 [(set (match_operand:X87MODEI 0 "register_operand" "")
5080 (fix:X87MODEI (match_operand 1 "register_operand" "")))
5081 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
5082 (clobber (match_scratch 3 ""))]
5084 [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
5085 (clobber (match_dup 3))])
5086 (set (match_dup 0) (match_dup 2))]
5090 [(set (match_operand:X87MODEI 0 "memory_operand" "")
5091 (fix:X87MODEI (match_operand 1 "register_operand" "")))
5092 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
5093 (clobber (match_scratch 3 ""))]
5095 [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
5096 (clobber (match_dup 3))])]
5099 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
5100 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
5101 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
5102 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
5103 ;; function in i386.c.
5104 (define_insn_and_split "*fix_trunc<mode>_i387_1"
5105 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
5106 (fix:X87MODEI (match_operand 1 "register_operand" "")))
5107 (clobber (reg:CC FLAGS_REG))]
5108 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5110 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
5111 && (TARGET_64BIT || <MODE>mode != DImode))
5112 && !(reload_completed || reload_in_progress)"
5117 ix86_optimize_mode_switching[I387_TRUNC] = 1;
5119 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
5120 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
5121 if (memory_operand (operands[0], VOIDmode))
5122 emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
5123 operands[2], operands[3]));
5126 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
5127 emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
5128 operands[2], operands[3],
5133 [(set_attr "type" "fistp")
5134 (set_attr "i387_cw" "trunc")
5135 (set_attr "mode" "<MODE>")])
5137 (define_insn "fix_truncdi_i387"
5138 [(set (match_operand:DI 0 "memory_operand" "=m")
5139 (fix:DI (match_operand 1 "register_operand" "f")))
5140 (use (match_operand:HI 2 "memory_operand" "m"))
5141 (use (match_operand:HI 3 "memory_operand" "m"))
5142 (clobber (match_scratch:XF 4 "=&1f"))]
5143 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5145 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
5146 "* return output_fix_trunc (insn, operands, 0);"
5147 [(set_attr "type" "fistp")
5148 (set_attr "i387_cw" "trunc")
5149 (set_attr "mode" "DI")])
5151 (define_insn "fix_truncdi_i387_with_temp"
5152 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
5153 (fix:DI (match_operand 1 "register_operand" "f,f")))
5154 (use (match_operand:HI 2 "memory_operand" "m,m"))
5155 (use (match_operand:HI 3 "memory_operand" "m,m"))
5156 (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
5157 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
5158 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5160 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
5162 [(set_attr "type" "fistp")
5163 (set_attr "i387_cw" "trunc")
5164 (set_attr "mode" "DI")])
5167 [(set (match_operand:DI 0 "register_operand" "")
5168 (fix:DI (match_operand 1 "register_operand" "")))
5169 (use (match_operand:HI 2 "memory_operand" ""))
5170 (use (match_operand:HI 3 "memory_operand" ""))
5171 (clobber (match_operand:DI 4 "memory_operand" ""))
5172 (clobber (match_scratch 5 ""))]
5174 [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
5177 (clobber (match_dup 5))])
5178 (set (match_dup 0) (match_dup 4))]
5182 [(set (match_operand:DI 0 "memory_operand" "")
5183 (fix:DI (match_operand 1 "register_operand" "")))
5184 (use (match_operand:HI 2 "memory_operand" ""))
5185 (use (match_operand:HI 3 "memory_operand" ""))
5186 (clobber (match_operand:DI 4 "memory_operand" ""))
5187 (clobber (match_scratch 5 ""))]
5189 [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
5192 (clobber (match_dup 5))])]
5195 (define_insn "fix_trunc<mode>_i387"
5196 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
5197 (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
5198 (use (match_operand:HI 2 "memory_operand" "m"))
5199 (use (match_operand:HI 3 "memory_operand" "m"))]
5200 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5202 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
5203 "* return output_fix_trunc (insn, operands, 0);"
5204 [(set_attr "type" "fistp")
5205 (set_attr "i387_cw" "trunc")
5206 (set_attr "mode" "<MODE>")])
5208 (define_insn "fix_trunc<mode>_i387_with_temp"
5209 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
5210 (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
5211 (use (match_operand:HI 2 "memory_operand" "m,m"))
5212 (use (match_operand:HI 3 "memory_operand" "m,m"))
5213 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
5214 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
5216 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
5218 [(set_attr "type" "fistp")
5219 (set_attr "i387_cw" "trunc")
5220 (set_attr "mode" "<MODE>")])
5223 [(set (match_operand:X87MODEI12 0 "register_operand" "")
5224 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
5225 (use (match_operand:HI 2 "memory_operand" ""))
5226 (use (match_operand:HI 3 "memory_operand" ""))
5227 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
5229 [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
5231 (use (match_dup 3))])
5232 (set (match_dup 0) (match_dup 4))]
5236 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
5237 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
5238 (use (match_operand:HI 2 "memory_operand" ""))
5239 (use (match_operand:HI 3 "memory_operand" ""))
5240 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
5242 [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
5244 (use (match_dup 3))])]
5247 (define_insn "x86_fnstcw_1"
5248 [(set (match_operand:HI 0 "memory_operand" "=m")
5249 (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
5252 [(set_attr "length" "2")
5253 (set_attr "mode" "HI")
5254 (set_attr "unit" "i387")])
5256 (define_insn "x86_fldcw_1"
5257 [(set (reg:HI FPCR_REG)
5258 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
5261 [(set_attr "length" "2")
5262 (set_attr "mode" "HI")
5263 (set_attr "unit" "i387")
5264 (set_attr "athlon_decode" "vector")
5265 (set_attr "amdfam10_decode" "vector")])
5267 ;; Conversion between fixed point and floating point.
5269 ;; Even though we only accept memory inputs, the backend _really_
5270 ;; wants to be able to do this between registers.
5272 (define_expand "floathi<mode>2"
5273 [(set (match_operand:X87MODEF 0 "register_operand" "")
5274 (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
5276 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5277 || TARGET_MIX_SSE_I387)"
5280 ;; Pre-reload splitter to add memory clobber to the pattern.
5281 (define_insn_and_split "*floathi<mode>2_1"
5282 [(set (match_operand:X87MODEF 0 "register_operand" "")
5283 (float:X87MODEF (match_operand:HI 1 "register_operand" "")))]
5285 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5286 || TARGET_MIX_SSE_I387)
5287 && !(reload_completed || reload_in_progress)"
5290 [(parallel [(set (match_dup 0)
5291 (float:X87MODEF (match_dup 1)))
5292 (clobber (match_dup 2))])]
5293 "operands[2] = assign_386_stack_local (HImode, SLOT_TEMP);")
5295 (define_insn "*floathi<mode>2_i387_with_temp"
5296 [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5297 (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))
5298 (clobber (match_operand:HI 2 "memory_operand" "=m,m"))]
5300 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5301 || TARGET_MIX_SSE_I387)"
5303 [(set_attr "type" "fmov,multi")
5304 (set_attr "mode" "<MODE>")
5305 (set_attr "unit" "*,i387")
5306 (set_attr "fp_int_src" "true")])
5308 (define_insn "*floathi<mode>2_i387"
5309 [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5310 (float:X87MODEF (match_operand:HI 1 "memory_operand" "m")))]
5312 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5313 || TARGET_MIX_SSE_I387)"
5315 [(set_attr "type" "fmov")
5316 (set_attr "mode" "<MODE>")
5317 (set_attr "fp_int_src" "true")])
5320 [(set (match_operand:X87MODEF 0 "register_operand" "")
5321 (float:X87MODEF (match_operand:HI 1 "register_operand" "")))
5322 (clobber (match_operand:HI 2 "memory_operand" ""))]
5324 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5325 || TARGET_MIX_SSE_I387)
5326 && reload_completed"
5327 [(set (match_dup 2) (match_dup 1))
5328 (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5332 [(set (match_operand:X87MODEF 0 "register_operand" "")
5333 (float:X87MODEF (match_operand:HI 1 "memory_operand" "")))
5334 (clobber (match_operand:HI 2 "memory_operand" ""))]
5336 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5337 || TARGET_MIX_SSE_I387)
5338 && reload_completed"
5339 [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
5342 (define_expand "float<SSEMODEI24:mode><X87MODEF:mode>2"
5343 [(set (match_operand:X87MODEF 0 "register_operand" "")
5345 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "")))]
5347 || ((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5348 && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)"
5351 if (!((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5352 && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
5353 && !X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode))
5355 rtx reg = gen_reg_rtx (XFmode);
5356 emit_insn (gen_float<SSEMODEI24:mode>xf2 (reg, operands[1]));
5357 /* Avoid references to nonexistent function in dead code in XFmode case. */
5358 #define gen_truncxfxf2 gen_truncxfdf2
5359 emit_insn (gen_truncxf<X87MODEF:mode>2 (operands[0], reg));
5360 #undef gen_truncxfxf2
5365 ;; Pre-reload splitter to add memory clobber to the pattern.
5366 (define_insn_and_split "*float<SSEMODEI24:mode><X87MODEF:mode>2_1"
5367 [(set (match_operand:X87MODEF 0 "register_operand" "")
5368 (float:X87MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))]
5370 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode)
5371 && (!((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5372 && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
5373 || TARGET_MIX_SSE_I387))
5374 || ((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5375 && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
5376 && ((<SSEMODEI24:MODE>mode == SImode
5377 && TARGET_SSE2 && TARGET_USE_VECTOR_CONVERTS
5378 && optimize_function_for_speed_p (cfun)
5379 && flag_trapping_math)
5380 || !(TARGET_INTER_UNIT_CONVERSIONS
5381 || optimize_function_for_size_p (cfun)))))
5382 && !(reload_completed || reload_in_progress)"
5385 [(parallel [(set (match_dup 0) (float:X87MODEF (match_dup 1)))
5386 (clobber (match_dup 2))])]
5388 operands[2] = assign_386_stack_local (<SSEMODEI24:MODE>mode, SLOT_TEMP);
5390 /* Avoid store forwarding (partial memory) stall penalty
5391 by passing DImode value through XMM registers. */
5392 if (<SSEMODEI24:MODE>mode == DImode && !TARGET_64BIT
5393 && TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5394 && optimize_function_for_speed_p (cfun))
5396 emit_insn (gen_floatdi<X87MODEF:mode>2_i387_with_xmm (operands[0],
5403 (define_insn "*floatsi<mode>2_vector_mixed_with_temp"
5404 [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x,x")
5406 (match_operand:SI 1 "nonimmediate_operand" "m,?r,r,m,!x")))
5407 (clobber (match_operand:SI 2 "memory_operand" "=X,m,m,X,m"))]
5408 "TARGET_SSE2 && TARGET_MIX_SSE_I387
5409 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
5411 [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
5412 (set_attr "mode" "<MODE>,<MODE>,<MODE>,<MODE>,<ssevecmode>")
5413 (set_attr "unit" "*,i387,*,*,*")
5414 (set_attr "athlon_decode" "*,*,double,direct,double")
5415 (set_attr "amdfam10_decode" "*,*,vector,double,double")
5416 (set_attr "fp_int_src" "true")])
5418 (define_insn "*floatsi<mode>2_vector_mixed"
5419 [(set (match_operand:MODEF 0 "register_operand" "=f,x")
5420 (float:MODEF (match_operand:SI 1 "memory_operand" "m,m")))]
5421 "TARGET_SSE2 && TARGET_MIX_SSE_I387
5422 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
5426 [(set_attr "type" "fmov,sseicvt")
5427 (set_attr "mode" "<MODE>,<ssevecmode>")
5428 (set_attr "unit" "i387,*")
5429 (set_attr "athlon_decode" "*,direct")
5430 (set_attr "amdfam10_decode" "*,double")
5431 (set_attr "fp_int_src" "true")])
5433 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_with_temp"
5434 [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
5436 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,?r,r,m")))
5437 (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=X,m,m,X"))]
5438 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5439 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387"
5441 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
5442 (set_attr "mode" "<MODEF:MODE>")
5443 (set_attr "unit" "*,i387,*,*")
5444 (set_attr "athlon_decode" "*,*,double,direct")
5445 (set_attr "amdfam10_decode" "*,*,vector,double")
5446 (set_attr "fp_int_src" "true")])
5449 [(set (match_operand:MODEF 0 "register_operand" "")
5450 (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5451 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5452 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5453 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5454 && TARGET_INTER_UNIT_CONVERSIONS
5456 && (SSE_REG_P (operands[0])
5457 || (GET_CODE (operands[0]) == SUBREG
5458 && SSE_REG_P (operands[0])))"
5459 [(set (match_dup 0) (float:MODEF (match_dup 1)))]
5463 [(set (match_operand:MODEF 0 "register_operand" "")
5464 (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5465 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5466 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5467 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5468 && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5470 && (SSE_REG_P (operands[0])
5471 || (GET_CODE (operands[0]) == SUBREG
5472 && SSE_REG_P (operands[0])))"
5473 [(set (match_dup 2) (match_dup 1))
5474 (set (match_dup 0) (float:MODEF (match_dup 2)))]
5477 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_interunit"
5478 [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
5480 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,r,m")))]
5481 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5482 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5483 && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5486 %vcvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %d0|%d0, %1}
5487 %vcvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %d0|%d0, %1}"
5488 [(set_attr "type" "fmov,sseicvt,sseicvt")
5489 (set_attr "prefix" "orig,maybe_vex,maybe_vex")
5490 (set_attr "mode" "<MODEF:MODE>")
5491 (set_attr "unit" "i387,*,*")
5492 (set_attr "athlon_decode" "*,double,direct")
5493 (set_attr "amdfam10_decode" "*,vector,double")
5494 (set_attr "fp_int_src" "true")])
5496 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_nointerunit"
5497 [(set (match_operand:MODEF 0 "register_operand" "=f,x")
5499 (match_operand:SSEMODEI24 1 "memory_operand" "m,m")))]
5500 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5501 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5502 && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5505 %vcvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %d0|%d0, %1}"
5506 [(set_attr "type" "fmov,sseicvt")
5507 (set_attr "prefix" "orig,maybe_vex")
5508 (set_attr "mode" "<MODEF:MODE>")
5509 (set_attr "athlon_decode" "*,direct")
5510 (set_attr "amdfam10_decode" "*,double")
5511 (set_attr "fp_int_src" "true")])
5513 (define_insn "*floatsi<mode>2_vector_sse_with_temp"
5514 [(set (match_operand:MODEF 0 "register_operand" "=x,x,x")
5516 (match_operand:SI 1 "nonimmediate_operand" "r,m,!x")))
5517 (clobber (match_operand:SI 2 "memory_operand" "=m,X,m"))]
5518 "TARGET_SSE2 && TARGET_SSE_MATH
5519 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
5521 [(set_attr "type" "sseicvt")
5522 (set_attr "mode" "<MODE>,<MODE>,<ssevecmode>")
5523 (set_attr "athlon_decode" "double,direct,double")
5524 (set_attr "amdfam10_decode" "vector,double,double")
5525 (set_attr "fp_int_src" "true")])
5527 (define_insn "*floatsi<mode>2_vector_sse"
5528 [(set (match_operand:MODEF 0 "register_operand" "=x")
5529 (float:MODEF (match_operand:SI 1 "memory_operand" "m")))]
5530 "TARGET_SSE2 && TARGET_SSE_MATH
5531 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
5533 [(set_attr "type" "sseicvt")
5534 (set_attr "mode" "<MODE>")
5535 (set_attr "athlon_decode" "direct")
5536 (set_attr "amdfam10_decode" "double")
5537 (set_attr "fp_int_src" "true")])
5540 [(set (match_operand:MODEF 0 "register_operand" "")
5541 (float:MODEF (match_operand:SI 1 "register_operand" "")))
5542 (clobber (match_operand:SI 2 "memory_operand" ""))]
5543 "TARGET_SSE2 && TARGET_SSE_MATH
5544 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5546 && (SSE_REG_P (operands[0])
5547 || (GET_CODE (operands[0]) == SUBREG
5548 && SSE_REG_P (operands[0])))"
5551 rtx op1 = operands[1];
5553 operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5555 if (GET_CODE (op1) == SUBREG)
5556 op1 = SUBREG_REG (op1);
5558 if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
5560 operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5561 emit_insn (gen_sse2_loadld (operands[4],
5562 CONST0_RTX (V4SImode), operands[1]));
5564 /* We can ignore possible trapping value in the
5565 high part of SSE register for non-trapping math. */
5566 else if (SSE_REG_P (op1) && !flag_trapping_math)
5567 operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5570 operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5571 emit_move_insn (operands[2], operands[1]);
5572 emit_insn (gen_sse2_loadld (operands[4],
5573 CONST0_RTX (V4SImode), operands[2]));
5576 (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5581 [(set (match_operand:MODEF 0 "register_operand" "")
5582 (float:MODEF (match_operand:SI 1 "memory_operand" "")))
5583 (clobber (match_operand:SI 2 "memory_operand" ""))]
5584 "TARGET_SSE2 && TARGET_SSE_MATH
5585 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5587 && (SSE_REG_P (operands[0])
5588 || (GET_CODE (operands[0]) == SUBREG
5589 && SSE_REG_P (operands[0])))"
5592 operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5594 operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5596 emit_insn (gen_sse2_loadld (operands[4],
5597 CONST0_RTX (V4SImode), operands[1]));
5599 (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5604 [(set (match_operand:MODEF 0 "register_operand" "")
5605 (float:MODEF (match_operand:SI 1 "register_operand" "")))]
5606 "TARGET_SSE2 && TARGET_SSE_MATH
5607 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5609 && (SSE_REG_P (operands[0])
5610 || (GET_CODE (operands[0]) == SUBREG
5611 && SSE_REG_P (operands[0])))"
5614 rtx op1 = operands[1];
5616 operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5618 if (GET_CODE (op1) == SUBREG)
5619 op1 = SUBREG_REG (op1);
5621 if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
5623 operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5624 emit_insn (gen_sse2_loadld (operands[4],
5625 CONST0_RTX (V4SImode), operands[1]));
5627 /* We can ignore possible trapping value in the
5628 high part of SSE register for non-trapping math. */
5629 else if (SSE_REG_P (op1) && !flag_trapping_math)
5630 operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5634 (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5639 [(set (match_operand:MODEF 0 "register_operand" "")
5640 (float:MODEF (match_operand:SI 1 "memory_operand" "")))]
5641 "TARGET_SSE2 && TARGET_SSE_MATH
5642 && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5644 && (SSE_REG_P (operands[0])
5645 || (GET_CODE (operands[0]) == SUBREG
5646 && SSE_REG_P (operands[0])))"
5649 operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5651 operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5653 emit_insn (gen_sse2_loadld (operands[4],
5654 CONST0_RTX (V4SImode), operands[1]));
5656 (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5660 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_with_temp"
5661 [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5663 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "r,m")))
5664 (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=m,X"))]
5665 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5666 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH"
5668 [(set_attr "type" "sseicvt")
5669 (set_attr "mode" "<MODEF:MODE>")
5670 (set_attr "athlon_decode" "double,direct")
5671 (set_attr "amdfam10_decode" "vector,double")
5672 (set_attr "fp_int_src" "true")])
5674 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_interunit"
5675 [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5677 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "r,m")))]
5678 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5679 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5680 && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5681 "%vcvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %d0|%d0, %1}"
5682 [(set_attr "type" "sseicvt")
5683 (set_attr "prefix" "maybe_vex")
5684 (set_attr "mode" "<MODEF:MODE>")
5685 (set_attr "athlon_decode" "double,direct")
5686 (set_attr "amdfam10_decode" "vector,double")
5687 (set_attr "fp_int_src" "true")])
5690 [(set (match_operand:MODEF 0 "register_operand" "")
5691 (float:MODEF (match_operand:SSEMODEI24 1 "nonimmediate_operand" "")))
5692 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5693 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5694 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5695 && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5697 && (SSE_REG_P (operands[0])
5698 || (GET_CODE (operands[0]) == SUBREG
5699 && SSE_REG_P (operands[0])))"
5700 [(set (match_dup 0) (float:MODEF (match_dup 1)))]
5703 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_nointerunit"
5704 [(set (match_operand:MODEF 0 "register_operand" "=x")
5706 (match_operand:SSEMODEI24 1 "memory_operand" "m")))]
5707 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5708 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5709 && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5710 "%vcvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %d0|%d0, %1}"
5711 [(set_attr "type" "sseicvt")
5712 (set_attr "prefix" "maybe_vex")
5713 (set_attr "mode" "<MODEF:MODE>")
5714 (set_attr "athlon_decode" "direct")
5715 (set_attr "amdfam10_decode" "double")
5716 (set_attr "fp_int_src" "true")])
5719 [(set (match_operand:MODEF 0 "register_operand" "")
5720 (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5721 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5722 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5723 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5724 && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5726 && (SSE_REG_P (operands[0])
5727 || (GET_CODE (operands[0]) == SUBREG
5728 && SSE_REG_P (operands[0])))"
5729 [(set (match_dup 2) (match_dup 1))
5730 (set (match_dup 0) (float:MODEF (match_dup 2)))]
5734 [(set (match_operand:MODEF 0 "register_operand" "")
5735 (float:MODEF (match_operand:SSEMODEI24 1 "memory_operand" "")))
5736 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5737 "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5738 && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5740 && (SSE_REG_P (operands[0])
5741 || (GET_CODE (operands[0]) == SUBREG
5742 && SSE_REG_P (operands[0])))"
5743 [(set (match_dup 0) (float:MODEF (match_dup 1)))]
5746 (define_insn "*float<SSEMODEI24:mode><X87MODEF:mode>2_i387_with_temp"
5747 [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5749 (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,?r")))
5750 (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=X,m"))]
5752 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode)"
5756 [(set_attr "type" "fmov,multi")
5757 (set_attr "mode" "<X87MODEF:MODE>")
5758 (set_attr "unit" "*,i387")
5759 (set_attr "fp_int_src" "true")])
5761 (define_insn "*float<SSEMODEI24:mode><X87MODEF:mode>2_i387"
5762 [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5764 (match_operand:SSEMODEI24 1 "memory_operand" "m")))]
5766 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode)"
5768 [(set_attr "type" "fmov")
5769 (set_attr "mode" "<X87MODEF:MODE>")
5770 (set_attr "fp_int_src" "true")])
5773 [(set (match_operand:X87MODEF 0 "register_operand" "")
5774 (float:X87MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5775 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5777 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode)
5779 && FP_REG_P (operands[0])"
5780 [(set (match_dup 2) (match_dup 1))
5781 (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5785 [(set (match_operand:X87MODEF 0 "register_operand" "")
5786 (float:X87MODEF (match_operand:SSEMODEI24 1 "memory_operand" "")))
5787 (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5789 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SSEMODEI24:MODE>mode)
5791 && FP_REG_P (operands[0])"
5792 [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
5795 ;; Avoid store forwarding (partial memory) stall penalty
5796 ;; by passing DImode value through XMM registers. */
5798 (define_insn "floatdi<X87MODEF:mode>2_i387_with_xmm"
5799 [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5801 (match_operand:DI 1 "nonimmediate_operand" "m,?r")))
5802 (clobber (match_scratch:V4SI 3 "=X,x"))
5803 (clobber (match_scratch:V4SI 4 "=X,x"))
5804 (clobber (match_operand:DI 2 "memory_operand" "=X,m"))]
5805 "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5806 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5807 && !TARGET_64BIT && optimize_function_for_speed_p (cfun)"
5809 [(set_attr "type" "multi")
5810 (set_attr "mode" "<X87MODEF:MODE>")
5811 (set_attr "unit" "i387")
5812 (set_attr "fp_int_src" "true")])
5815 [(set (match_operand:X87MODEF 0 "register_operand" "")
5816 (float:X87MODEF (match_operand:DI 1 "register_operand" "")))
5817 (clobber (match_scratch:V4SI 3 ""))
5818 (clobber (match_scratch:V4SI 4 ""))
5819 (clobber (match_operand:DI 2 "memory_operand" ""))]
5820 "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5821 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5822 && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5824 && FP_REG_P (operands[0])"
5825 [(set (match_dup 2) (match_dup 3))
5826 (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5828 /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
5829 Assemble the 64-bit DImode value in an xmm register. */
5830 emit_insn (gen_sse2_loadld (operands[3], CONST0_RTX (V4SImode),
5831 gen_rtx_SUBREG (SImode, operands[1], 0)));
5832 emit_insn (gen_sse2_loadld (operands[4], CONST0_RTX (V4SImode),
5833 gen_rtx_SUBREG (SImode, operands[1], 4)));
5834 emit_insn (gen_sse2_punpckldq (operands[3], operands[3], operands[4]));
5836 operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
5840 [(set (match_operand:X87MODEF 0 "register_operand" "")
5841 (float:X87MODEF (match_operand:DI 1 "memory_operand" "")))
5842 (clobber (match_scratch:V4SI 3 ""))
5843 (clobber (match_scratch:V4SI 4 ""))
5844 (clobber (match_operand:DI 2 "memory_operand" ""))]
5845 "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5846 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5847 && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5849 && FP_REG_P (operands[0])"
5850 [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
5853 ;; Avoid store forwarding (partial memory) stall penalty by extending
5854 ;; SImode value to DImode through XMM register instead of pushing two
5855 ;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES
5856 ;; targets benefit from this optimization. Also note that fild
5857 ;; loads from memory only.
5859 (define_insn "*floatunssi<mode>2_1"
5860 [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5861 (unsigned_float:X87MODEF
5862 (match_operand:SI 1 "nonimmediate_operand" "x,m")))
5863 (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
5864 (clobber (match_scratch:SI 3 "=X,x"))]
5866 && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5869 [(set_attr "type" "multi")
5870 (set_attr "mode" "<MODE>")])
5873 [(set (match_operand:X87MODEF 0 "register_operand" "")
5874 (unsigned_float:X87MODEF
5875 (match_operand:SI 1 "register_operand" "")))
5876 (clobber (match_operand:DI 2 "memory_operand" ""))
5877 (clobber (match_scratch:SI 3 ""))]
5879 && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5881 && reload_completed"
5882 [(set (match_dup 2) (match_dup 1))
5884 (float:X87MODEF (match_dup 2)))]
5885 "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);")
5888 [(set (match_operand:X87MODEF 0 "register_operand" "")
5889 (unsigned_float:X87MODEF
5890 (match_operand:SI 1 "memory_operand" "")))
5891 (clobber (match_operand:DI 2 "memory_operand" ""))
5892 (clobber (match_scratch:SI 3 ""))]
5894 && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5896 && reload_completed"
5897 [(set (match_dup 2) (match_dup 3))
5899 (float:X87MODEF (match_dup 2)))]
5901 emit_move_insn (operands[3], operands[1]);
5902 operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0);
5905 (define_expand "floatunssi<mode>2"
5907 [(set (match_operand:X87MODEF 0 "register_operand" "")
5908 (unsigned_float:X87MODEF
5909 (match_operand:SI 1 "nonimmediate_operand" "")))
5910 (clobber (match_dup 2))
5911 (clobber (match_scratch:SI 3 ""))])]
5913 && ((TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5915 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
5917 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5919 ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5924 enum ix86_stack_slot slot = (virtuals_instantiated
5927 operands[2] = assign_386_stack_local (DImode, slot);
5931 (define_expand "floatunsdisf2"
5932 [(use (match_operand:SF 0 "register_operand" ""))
5933 (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5934 "TARGET_64BIT && TARGET_SSE_MATH"
5935 "x86_emit_floatuns (operands); DONE;")
5937 (define_expand "floatunsdidf2"
5938 [(use (match_operand:DF 0 "register_operand" ""))
5939 (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5940 "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5941 && TARGET_SSE2 && TARGET_SSE_MATH"
5944 x86_emit_floatuns (operands);
5946 ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5952 ;; %%% splits for addditi3
5954 (define_expand "addti3"
5955 [(set (match_operand:TI 0 "nonimmediate_operand" "")
5956 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5957 (match_operand:TI 2 "x86_64_general_operand" "")))]
5959 "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;")
5961 (define_insn "*addti3_1"
5962 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
5963 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0")
5964 (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
5965 (clobber (reg:CC FLAGS_REG))]
5966 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)"
5970 [(set (match_operand:TI 0 "nonimmediate_operand" "")
5971 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5972 (match_operand:TI 2 "x86_64_general_operand" "")))
5973 (clobber (reg:CC FLAGS_REG))]
5974 "TARGET_64BIT && reload_completed"
5975 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
5977 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))])
5978 (parallel [(set (match_dup 3)
5979 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
5982 (clobber (reg:CC FLAGS_REG))])]
5983 "split_ti (&operands[0], 3, &operands[0], &operands[3]);")
5985 ;; %%% splits for addsidi3
5986 ; [(set (match_operand:DI 0 "nonimmediate_operand" "")
5987 ; (plus:DI (match_operand:DI 1 "general_operand" "")
5988 ; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
5990 (define_expand "adddi3"
5991 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5992 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5993 (match_operand:DI 2 "x86_64_general_operand" "")))]
5995 "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
5997 (define_insn "*adddi3_1"
5998 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
5999 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
6000 (match_operand:DI 2 "general_operand" "roiF,riF")))
6001 (clobber (reg:CC FLAGS_REG))]
6002 "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
6006 [(set (match_operand:DI 0 "nonimmediate_operand" "")
6007 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6008 (match_operand:DI 2 "general_operand" "")))
6009 (clobber (reg:CC FLAGS_REG))]
6010 "!TARGET_64BIT && reload_completed"
6011 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
6013 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
6014 (parallel [(set (match_dup 3)
6015 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
6018 (clobber (reg:CC FLAGS_REG))])]
6019 "split_di (&operands[0], 3, &operands[0], &operands[3]);")
6021 (define_insn "adddi3_carry_rex64"
6022 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6023 (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6024 (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
6025 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6026 (clobber (reg:CC FLAGS_REG))]
6027 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
6028 "adc{q}\t{%2, %0|%0, %2}"
6029 [(set_attr "type" "alu")
6030 (set_attr "use_carry" "1")
6031 (set_attr "pent_pair" "pu")
6032 (set_attr "mode" "DI")])
6034 (define_insn "*adddi3_cc_rex64"
6035 [(set (reg:CC FLAGS_REG)
6036 (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
6037 (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
6039 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6040 (plus:DI (match_dup 1) (match_dup 2)))]
6041 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
6042 "add{q}\t{%2, %0|%0, %2}"
6043 [(set_attr "type" "alu")
6044 (set_attr "mode" "DI")])
6046 (define_insn "*<plusminus_insn><mode>3_cc_overflow"
6047 [(set (reg:CCC FLAGS_REG)
6050 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6051 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6053 (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6054 (plusminus:SWI (match_dup 1) (match_dup 2)))]
6055 "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6056 "<plusminus_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6057 [(set_attr "type" "alu")
6058 (set_attr "mode" "<MODE>")])
6060 (define_insn "*add<mode>3_cconly_overflow"
6061 [(set (reg:CCC FLAGS_REG)
6063 (plus:SWI (match_operand:SWI 1 "nonimmediate_operand" "%0")
6064 (match_operand:SWI 2 "<general_operand>" "<r><i>m"))
6066 (clobber (match_scratch:SWI 0 "=<r>"))]
6067 "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
6068 "add{<imodesuffix>}\t{%2, %0|%0, %2}"
6069 [(set_attr "type" "alu")
6070 (set_attr "mode" "<MODE>")])
6072 (define_insn "*sub<mode>3_cconly_overflow"
6073 [(set (reg:CCC FLAGS_REG)
6075 (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
6076 (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
6079 "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
6080 [(set_attr "type" "icmp")
6081 (set_attr "mode" "<MODE>")])
6083 (define_insn "*<plusminus_insn>si3_zext_cc_overflow"
6084 [(set (reg:CCC FLAGS_REG)
6086 (plusminus:SI (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
6087 (match_operand:SI 2 "general_operand" "g"))
6089 (set (match_operand:DI 0 "register_operand" "=r")
6090 (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
6091 "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
6092 "<plusminus_mnemonic>{l}\t{%2, %k0|%k0, %2}"
6093 [(set_attr "type" "alu")
6094 (set_attr "mode" "SI")])
6096 (define_insn "addqi3_carry"
6097 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6098 (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6099 (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
6100 (match_operand:QI 2 "general_operand" "qn,qm")))
6101 (clobber (reg:CC FLAGS_REG))]
6102 "ix86_binary_operator_ok (PLUS, QImode, operands)"
6103 "adc{b}\t{%2, %0|%0, %2}"
6104 [(set_attr "type" "alu")
6105 (set_attr "use_carry" "1")
6106 (set_attr "pent_pair" "pu")
6107 (set_attr "mode" "QI")])
6109 (define_insn "addhi3_carry"
6110 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6111 (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6112 (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
6113 (match_operand:HI 2 "general_operand" "rn,rm")))
6114 (clobber (reg:CC FLAGS_REG))]
6115 "ix86_binary_operator_ok (PLUS, HImode, operands)"
6116 "adc{w}\t{%2, %0|%0, %2}"
6117 [(set_attr "type" "alu")
6118 (set_attr "use_carry" "1")
6119 (set_attr "pent_pair" "pu")
6120 (set_attr "mode" "HI")])
6122 (define_insn "addsi3_carry"
6123 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6124 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6125 (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
6126 (match_operand:SI 2 "general_operand" "ri,rm")))
6127 (clobber (reg:CC FLAGS_REG))]
6128 "ix86_binary_operator_ok (PLUS, SImode, operands)"
6129 "adc{l}\t{%2, %0|%0, %2}"
6130 [(set_attr "type" "alu")
6131 (set_attr "use_carry" "1")
6132 (set_attr "pent_pair" "pu")
6133 (set_attr "mode" "SI")])
6135 (define_insn "*addsi3_carry_zext"
6136 [(set (match_operand:DI 0 "register_operand" "=r")
6138 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6139 (match_operand:SI 1 "nonimmediate_operand" "%0"))
6140 (match_operand:SI 2 "general_operand" "g"))))
6141 (clobber (reg:CC FLAGS_REG))]
6142 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6143 "adc{l}\t{%2, %k0|%k0, %2}"
6144 [(set_attr "type" "alu")
6145 (set_attr "use_carry" "1")
6146 (set_attr "pent_pair" "pu")
6147 (set_attr "mode" "SI")])
6149 (define_insn "*addsi3_cc"
6150 [(set (reg:CC FLAGS_REG)
6151 (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
6152 (match_operand:SI 2 "general_operand" "ri,rm")]
6154 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6155 (plus:SI (match_dup 1) (match_dup 2)))]
6156 "ix86_binary_operator_ok (PLUS, SImode, operands)"
6157 "add{l}\t{%2, %0|%0, %2}"
6158 [(set_attr "type" "alu")
6159 (set_attr "mode" "SI")])
6161 (define_insn "addqi3_cc"
6162 [(set (reg:CC FLAGS_REG)
6163 (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
6164 (match_operand:QI 2 "general_operand" "qn,qm")]
6166 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6167 (plus:QI (match_dup 1) (match_dup 2)))]
6168 "ix86_binary_operator_ok (PLUS, QImode, operands)"
6169 "add{b}\t{%2, %0|%0, %2}"
6170 [(set_attr "type" "alu")
6171 (set_attr "mode" "QI")])
6173 (define_expand "addsi3"
6174 [(set (match_operand:SI 0 "nonimmediate_operand" "")
6175 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6176 (match_operand:SI 2 "general_operand" "")))]
6178 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
6180 (define_insn "*lea_1"
6181 [(set (match_operand:SI 0 "register_operand" "=r")
6182 (match_operand:SI 1 "no_seg_address_operand" "p"))]
6184 "lea{l}\t{%a1, %0|%0, %a1}"
6185 [(set_attr "type" "lea")
6186 (set_attr "mode" "SI")])
6188 (define_insn "*lea_1_rex64"
6189 [(set (match_operand:SI 0 "register_operand" "=r")
6190 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
6192 "lea{l}\t{%a1, %0|%0, %a1}"
6193 [(set_attr "type" "lea")
6194 (set_attr "mode" "SI")])
6196 (define_insn "*lea_1_zext"
6197 [(set (match_operand:DI 0 "register_operand" "=r")
6199 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
6201 "lea{l}\t{%a1, %k0|%k0, %a1}"
6202 [(set_attr "type" "lea")
6203 (set_attr "mode" "SI")])
6205 (define_insn "*lea_2_rex64"
6206 [(set (match_operand:DI 0 "register_operand" "=r")
6207 (match_operand:DI 1 "no_seg_address_operand" "p"))]
6209 "lea{q}\t{%a1, %0|%0, %a1}"
6210 [(set_attr "type" "lea")
6211 (set_attr "mode" "DI")])
6213 ;; The lea patterns for non-Pmodes needs to be matched by several
6214 ;; insns converted to real lea by splitters.
6216 (define_insn_and_split "*lea_general_1"
6217 [(set (match_operand 0 "register_operand" "=r")
6218 (plus (plus (match_operand 1 "index_register_operand" "l")
6219 (match_operand 2 "register_operand" "r"))
6220 (match_operand 3 "immediate_operand" "i")))]
6221 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
6222 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
6223 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6224 && GET_MODE (operands[0]) == GET_MODE (operands[1])
6225 && GET_MODE (operands[0]) == GET_MODE (operands[2])
6226 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6227 || GET_MODE (operands[3]) == VOIDmode)"
6229 "&& reload_completed"
6233 operands[0] = gen_lowpart (SImode, operands[0]);
6234 operands[1] = gen_lowpart (Pmode, operands[1]);
6235 operands[2] = gen_lowpart (Pmode, operands[2]);
6236 operands[3] = gen_lowpart (Pmode, operands[3]);
6237 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
6239 if (Pmode != SImode)
6240 pat = gen_rtx_SUBREG (SImode, pat, 0);
6241 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6244 [(set_attr "type" "lea")
6245 (set_attr "mode" "SI")])
6247 (define_insn_and_split "*lea_general_1_zext"
6248 [(set (match_operand:DI 0 "register_operand" "=r")
6250 (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
6251 (match_operand:SI 2 "register_operand" "r"))
6252 (match_operand:SI 3 "immediate_operand" "i"))))]
6255 "&& reload_completed"
6257 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
6259 (match_dup 3)) 0)))]
6261 operands[1] = gen_lowpart (Pmode, operands[1]);
6262 operands[2] = gen_lowpart (Pmode, operands[2]);
6263 operands[3] = gen_lowpart (Pmode, operands[3]);
6265 [(set_attr "type" "lea")
6266 (set_attr "mode" "SI")])
6268 (define_insn_and_split "*lea_general_2"
6269 [(set (match_operand 0 "register_operand" "=r")
6270 (plus (mult (match_operand 1 "index_register_operand" "l")
6271 (match_operand 2 "const248_operand" "i"))
6272 (match_operand 3 "nonmemory_operand" "ri")))]
6273 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
6274 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
6275 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6276 && GET_MODE (operands[0]) == GET_MODE (operands[1])
6277 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6278 || GET_MODE (operands[3]) == VOIDmode)"
6280 "&& reload_completed"
6284 operands[0] = gen_lowpart (SImode, operands[0]);
6285 operands[1] = gen_lowpart (Pmode, operands[1]);
6286 operands[3] = gen_lowpart (Pmode, operands[3]);
6287 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
6289 if (Pmode != SImode)
6290 pat = gen_rtx_SUBREG (SImode, pat, 0);
6291 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6294 [(set_attr "type" "lea")
6295 (set_attr "mode" "SI")])
6297 (define_insn_and_split "*lea_general_2_zext"
6298 [(set (match_operand:DI 0 "register_operand" "=r")
6300 (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
6301 (match_operand:SI 2 "const248_operand" "n"))
6302 (match_operand:SI 3 "nonmemory_operand" "ri"))))]
6305 "&& reload_completed"
6307 (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
6309 (match_dup 3)) 0)))]
6311 operands[1] = gen_lowpart (Pmode, operands[1]);
6312 operands[3] = gen_lowpart (Pmode, operands[3]);
6314 [(set_attr "type" "lea")
6315 (set_attr "mode" "SI")])
6317 (define_insn_and_split "*lea_general_3"
6318 [(set (match_operand 0 "register_operand" "=r")
6319 (plus (plus (mult (match_operand 1 "index_register_operand" "l")
6320 (match_operand 2 "const248_operand" "i"))
6321 (match_operand 3 "register_operand" "r"))
6322 (match_operand 4 "immediate_operand" "i")))]
6323 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
6324 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
6325 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6326 && GET_MODE (operands[0]) == GET_MODE (operands[1])
6327 && GET_MODE (operands[0]) == GET_MODE (operands[3])"
6329 "&& reload_completed"
6333 operands[0] = gen_lowpart (SImode, operands[0]);
6334 operands[1] = gen_lowpart (Pmode, operands[1]);
6335 operands[3] = gen_lowpart (Pmode, operands[3]);
6336 operands[4] = gen_lowpart (Pmode, operands[4]);
6337 pat = gen_rtx_PLUS (Pmode,
6338 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
6342 if (Pmode != SImode)
6343 pat = gen_rtx_SUBREG (SImode, pat, 0);
6344 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6347 [(set_attr "type" "lea")
6348 (set_attr "mode" "SI")])
6350 (define_insn_and_split "*lea_general_3_zext"
6351 [(set (match_operand:DI 0 "register_operand" "=r")
6353 (plus:SI (plus:SI (mult:SI
6354 (match_operand:SI 1 "index_register_operand" "l")
6355 (match_operand:SI 2 "const248_operand" "n"))
6356 (match_operand:SI 3 "register_operand" "r"))
6357 (match_operand:SI 4 "immediate_operand" "i"))))]
6360 "&& reload_completed"
6362 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
6365 (match_dup 4)) 0)))]
6367 operands[1] = gen_lowpart (Pmode, operands[1]);
6368 operands[3] = gen_lowpart (Pmode, operands[3]);
6369 operands[4] = gen_lowpart (Pmode, operands[4]);
6371 [(set_attr "type" "lea")
6372 (set_attr "mode" "SI")])
6374 (define_insn "*adddi_1_rex64"
6375 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
6376 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r,r")
6377 (match_operand:DI 2 "x86_64_general_operand" "rme,re,0,le")))
6378 (clobber (reg:CC FLAGS_REG))]
6379 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
6381 switch (get_attr_type (insn))
6384 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6385 return "lea{q}\t{%a2, %0|%0, %a2}";
6388 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6389 if (operands[2] == const1_rtx)
6390 return "inc{q}\t%0";
6393 gcc_assert (operands[2] == constm1_rtx);
6394 return "dec{q}\t%0";
6398 /* Use add as much as possible to replace lea for AGU optimization. */
6399 if (which_alternative == 2 && TARGET_OPT_AGU)
6400 return "add{q}\t{%1, %0|%0, %1}";
6402 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6404 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6405 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6406 if (CONST_INT_P (operands[2])
6407 /* Avoid overflows. */
6408 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6409 && (INTVAL (operands[2]) == 128
6410 || (INTVAL (operands[2]) < 0
6411 && INTVAL (operands[2]) != -128)))
6413 operands[2] = GEN_INT (-INTVAL (operands[2]));
6414 return "sub{q}\t{%2, %0|%0, %2}";
6416 return "add{q}\t{%2, %0|%0, %2}";
6420 (cond [(and (eq_attr "alternative" "2")
6421 (eq (symbol_ref "TARGET_OPT_AGU") (const_int 0)))
6422 (const_string "lea")
6423 (eq_attr "alternative" "3")
6424 (const_string "lea")
6425 ; Current assemblers are broken and do not allow @GOTOFF in
6426 ; ought but a memory context.
6427 (match_operand:DI 2 "pic_symbolic_operand" "")
6428 (const_string "lea")
6429 (match_operand:DI 2 "incdec_operand" "")
6430 (const_string "incdec")
6432 (const_string "alu")))
6433 (set_attr "mode" "DI")])
6435 ;; Convert lea to the lea pattern to avoid flags dependency.
6437 [(set (match_operand:DI 0 "register_operand" "")
6438 (plus:DI (match_operand:DI 1 "register_operand" "")
6439 (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
6440 (clobber (reg:CC FLAGS_REG))]
6441 "TARGET_64BIT && reload_completed
6442 && ix86_lea_for_add_ok (PLUS, insn, operands)"
6444 (plus:DI (match_dup 1)
6448 (define_insn "*adddi_2_rex64"
6449 [(set (reg FLAGS_REG)
6451 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
6452 (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
6454 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
6455 (plus:DI (match_dup 1) (match_dup 2)))]
6456 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6457 && ix86_binary_operator_ok (PLUS, DImode, operands)
6458 /* Current assemblers are broken and do not allow @GOTOFF in
6459 ought but a memory context. */
6460 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6462 switch (get_attr_type (insn))
6465 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6466 if (operands[2] == const1_rtx)
6467 return "inc{q}\t%0";
6470 gcc_assert (operands[2] == constm1_rtx);
6471 return "dec{q}\t%0";
6475 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6476 /* ???? We ought to handle there the 32bit case too
6477 - do we need new constraint? */
6478 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6479 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6480 if (CONST_INT_P (operands[2])
6481 /* Avoid overflows. */
6482 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6483 && (INTVAL (operands[2]) == 128
6484 || (INTVAL (operands[2]) < 0
6485 && INTVAL (operands[2]) != -128)))
6487 operands[2] = GEN_INT (-INTVAL (operands[2]));
6488 return "sub{q}\t{%2, %0|%0, %2}";
6490 return "add{q}\t{%2, %0|%0, %2}";
6494 (if_then_else (match_operand:DI 2 "incdec_operand" "")
6495 (const_string "incdec")
6496 (const_string "alu")))
6497 (set_attr "mode" "DI")])
6499 (define_insn "*adddi_3_rex64"
6500 [(set (reg FLAGS_REG)
6501 (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
6502 (match_operand:DI 1 "x86_64_general_operand" "%0")))
6503 (clobber (match_scratch:DI 0 "=r"))]
6505 && ix86_match_ccmode (insn, CCZmode)
6506 && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6507 /* Current assemblers are broken and do not allow @GOTOFF in
6508 ought but a memory context. */
6509 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6511 switch (get_attr_type (insn))
6514 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6515 if (operands[2] == const1_rtx)
6516 return "inc{q}\t%0";
6519 gcc_assert (operands[2] == constm1_rtx);
6520 return "dec{q}\t%0";
6524 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6525 /* ???? We ought to handle there the 32bit case too
6526 - do we need new constraint? */
6527 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6528 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6529 if (CONST_INT_P (operands[2])
6530 /* Avoid overflows. */
6531 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6532 && (INTVAL (operands[2]) == 128
6533 || (INTVAL (operands[2]) < 0
6534 && INTVAL (operands[2]) != -128)))
6536 operands[2] = GEN_INT (-INTVAL (operands[2]));
6537 return "sub{q}\t{%2, %0|%0, %2}";
6539 return "add{q}\t{%2, %0|%0, %2}";
6543 (if_then_else (match_operand:DI 2 "incdec_operand" "")
6544 (const_string "incdec")
6545 (const_string "alu")))
6546 (set_attr "mode" "DI")])
6548 ; For comparisons against 1, -1 and 128, we may generate better code
6549 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
6550 ; is matched then. We can't accept general immediate, because for
6551 ; case of overflows, the result is messed up.
6552 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
6554 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6555 ; only for comparisons not depending on it.
6556 (define_insn "*adddi_4_rex64"
6557 [(set (reg FLAGS_REG)
6558 (compare (match_operand:DI 1 "nonimmediate_operand" "0")
6559 (match_operand:DI 2 "x86_64_immediate_operand" "e")))
6560 (clobber (match_scratch:DI 0 "=rm"))]
6562 && ix86_match_ccmode (insn, CCGCmode)"
6564 switch (get_attr_type (insn))
6567 if (operands[2] == constm1_rtx)
6568 return "inc{q}\t%0";
6571 gcc_assert (operands[2] == const1_rtx);
6572 return "dec{q}\t%0";
6576 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6577 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6578 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6579 if ((INTVAL (operands[2]) == -128
6580 || (INTVAL (operands[2]) > 0
6581 && INTVAL (operands[2]) != 128))
6582 /* Avoid overflows. */
6583 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
6584 return "sub{q}\t{%2, %0|%0, %2}";
6585 operands[2] = GEN_INT (-INTVAL (operands[2]));
6586 return "add{q}\t{%2, %0|%0, %2}";
6590 (if_then_else (match_operand:DI 2 "incdec_operand" "")
6591 (const_string "incdec")
6592 (const_string "alu")))
6593 (set_attr "mode" "DI")])
6595 (define_insn "*adddi_5_rex64"
6596 [(set (reg FLAGS_REG)
6598 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
6599 (match_operand:DI 2 "x86_64_general_operand" "rme"))
6601 (clobber (match_scratch:DI 0 "=r"))]
6603 && ix86_match_ccmode (insn, CCGOCmode)
6604 && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6605 /* Current assemblers are broken and do not allow @GOTOFF in
6606 ought but a memory context. */
6607 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6609 switch (get_attr_type (insn))
6612 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6613 if (operands[2] == const1_rtx)
6614 return "inc{q}\t%0";
6617 gcc_assert (operands[2] == constm1_rtx);
6618 return "dec{q}\t%0";
6622 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6623 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6624 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6625 if (CONST_INT_P (operands[2])
6626 /* Avoid overflows. */
6627 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6628 && (INTVAL (operands[2]) == 128
6629 || (INTVAL (operands[2]) < 0
6630 && INTVAL (operands[2]) != -128)))
6632 operands[2] = GEN_INT (-INTVAL (operands[2]));
6633 return "sub{q}\t{%2, %0|%0, %2}";
6635 return "add{q}\t{%2, %0|%0, %2}";
6639 (if_then_else (match_operand:DI 2 "incdec_operand" "")
6640 (const_string "incdec")
6641 (const_string "alu")))
6642 (set_attr "mode" "DI")])
6645 (define_insn "*addsi_1"
6646 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r,r")
6647 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r,r")
6648 (match_operand:SI 2 "general_operand" "g,ri,0,li")))
6649 (clobber (reg:CC FLAGS_REG))]
6650 "ix86_binary_operator_ok (PLUS, SImode, operands)"
6652 switch (get_attr_type (insn))
6655 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6656 return "lea{l}\t{%a2, %0|%0, %a2}";
6659 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6660 if (operands[2] == const1_rtx)
6661 return "inc{l}\t%0";
6664 gcc_assert (operands[2] == constm1_rtx);
6665 return "dec{l}\t%0";
6669 /* Use add as much as possible to replace lea for AGU optimization. */
6670 if (which_alternative == 2 && TARGET_OPT_AGU)
6671 return "add{l}\t{%1, %0|%0, %1}";
6673 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6675 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6676 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6677 if (CONST_INT_P (operands[2])
6678 && (INTVAL (operands[2]) == 128
6679 || (INTVAL (operands[2]) < 0
6680 && INTVAL (operands[2]) != -128)))
6682 operands[2] = GEN_INT (-INTVAL (operands[2]));
6683 return "sub{l}\t{%2, %0|%0, %2}";
6685 return "add{l}\t{%2, %0|%0, %2}";
6689 (cond [(and (eq_attr "alternative" "2")
6690 (eq (symbol_ref "TARGET_OPT_AGU") (const_int 0)))
6691 (const_string "lea")
6692 (eq_attr "alternative" "3")
6693 (const_string "lea")
6694 ; Current assemblers are broken and do not allow @GOTOFF in
6695 ; ought but a memory context.
6696 (match_operand:SI 2 "pic_symbolic_operand" "")
6697 (const_string "lea")
6698 (match_operand:SI 2 "incdec_operand" "")
6699 (const_string "incdec")
6701 (const_string "alu")))
6702 (set_attr "mode" "SI")])
6704 ;; Convert lea to the lea pattern to avoid flags dependency.
6706 [(set (match_operand 0 "register_operand" "")
6707 (plus (match_operand 1 "register_operand" "")
6708 (match_operand 2 "nonmemory_operand" "")))
6709 (clobber (reg:CC FLAGS_REG))]
6710 "reload_completed && ix86_lea_for_add_ok (PLUS, insn, operands)"
6714 /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
6715 may confuse gen_lowpart. */
6716 if (GET_MODE (operands[0]) != Pmode)
6718 operands[1] = gen_lowpart (Pmode, operands[1]);
6719 operands[2] = gen_lowpart (Pmode, operands[2]);
6721 operands[0] = gen_lowpart (SImode, operands[0]);
6722 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
6723 if (Pmode != SImode)
6724 pat = gen_rtx_SUBREG (SImode, pat, 0);
6725 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6729 ;; It may seem that nonimmediate operand is proper one for operand 1.
6730 ;; The addsi_1 pattern allows nonimmediate operand at that place and
6731 ;; we take care in ix86_binary_operator_ok to not allow two memory
6732 ;; operands so proper swapping will be done in reload. This allow
6733 ;; patterns constructed from addsi_1 to match.
6734 (define_insn "addsi_1_zext"
6735 [(set (match_operand:DI 0 "register_operand" "=r,r")
6737 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
6738 (match_operand:SI 2 "general_operand" "g,li"))))
6739 (clobber (reg:CC FLAGS_REG))]
6740 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6742 switch (get_attr_type (insn))
6745 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6746 return "lea{l}\t{%a2, %k0|%k0, %a2}";
6749 if (operands[2] == const1_rtx)
6750 return "inc{l}\t%k0";
6753 gcc_assert (operands[2] == constm1_rtx);
6754 return "dec{l}\t%k0";
6758 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6759 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6760 if (CONST_INT_P (operands[2])
6761 && (INTVAL (operands[2]) == 128
6762 || (INTVAL (operands[2]) < 0
6763 && INTVAL (operands[2]) != -128)))
6765 operands[2] = GEN_INT (-INTVAL (operands[2]));
6766 return "sub{l}\t{%2, %k0|%k0, %2}";
6768 return "add{l}\t{%2, %k0|%k0, %2}";
6772 (cond [(eq_attr "alternative" "1")
6773 (const_string "lea")
6774 ; Current assemblers are broken and do not allow @GOTOFF in
6775 ; ought but a memory context.
6776 (match_operand:SI 2 "pic_symbolic_operand" "")
6777 (const_string "lea")
6778 (match_operand:SI 2 "incdec_operand" "")
6779 (const_string "incdec")
6781 (const_string "alu")))
6782 (set_attr "mode" "SI")])
6784 ;; Convert lea to the lea pattern to avoid flags dependency.
6786 [(set (match_operand:DI 0 "register_operand" "")
6788 (plus:SI (match_operand:SI 1 "register_operand" "")
6789 (match_operand:SI 2 "nonmemory_operand" ""))))
6790 (clobber (reg:CC FLAGS_REG))]
6791 "TARGET_64BIT && reload_completed
6792 && true_regnum (operands[0]) != true_regnum (operands[1])"
6794 (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
6796 operands[1] = gen_lowpart (Pmode, operands[1]);
6797 operands[2] = gen_lowpart (Pmode, operands[2]);
6800 (define_insn "*addsi_2"
6801 [(set (reg FLAGS_REG)
6803 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
6804 (match_operand:SI 2 "general_operand" "g,ri"))
6806 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
6807 (plus:SI (match_dup 1) (match_dup 2)))]
6808 "ix86_match_ccmode (insn, CCGOCmode)
6809 && ix86_binary_operator_ok (PLUS, SImode, operands)
6810 /* Current assemblers are broken and do not allow @GOTOFF in
6811 ought but a memory context. */
6812 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6814 switch (get_attr_type (insn))
6817 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6818 if (operands[2] == const1_rtx)
6819 return "inc{l}\t%0";
6822 gcc_assert (operands[2] == constm1_rtx);
6823 return "dec{l}\t%0";
6827 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6828 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6829 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6830 if (CONST_INT_P (operands[2])
6831 && (INTVAL (operands[2]) == 128
6832 || (INTVAL (operands[2]) < 0
6833 && INTVAL (operands[2]) != -128)))
6835 operands[2] = GEN_INT (-INTVAL (operands[2]));
6836 return "sub{l}\t{%2, %0|%0, %2}";
6838 return "add{l}\t{%2, %0|%0, %2}";
6842 (if_then_else (match_operand:SI 2 "incdec_operand" "")
6843 (const_string "incdec")
6844 (const_string "alu")))
6845 (set_attr "mode" "SI")])
6847 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6848 (define_insn "*addsi_2_zext"
6849 [(set (reg FLAGS_REG)
6851 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6852 (match_operand:SI 2 "general_operand" "g"))
6854 (set (match_operand:DI 0 "register_operand" "=r")
6855 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6856 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6857 && ix86_binary_operator_ok (PLUS, SImode, operands)
6858 /* Current assemblers are broken and do not allow @GOTOFF in
6859 ought but a memory context. */
6860 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6862 switch (get_attr_type (insn))
6865 if (operands[2] == const1_rtx)
6866 return "inc{l}\t%k0";
6869 gcc_assert (operands[2] == constm1_rtx);
6870 return "dec{l}\t%k0";
6874 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6875 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6876 if (CONST_INT_P (operands[2])
6877 && (INTVAL (operands[2]) == 128
6878 || (INTVAL (operands[2]) < 0
6879 && INTVAL (operands[2]) != -128)))
6881 operands[2] = GEN_INT (-INTVAL (operands[2]));
6882 return "sub{l}\t{%2, %k0|%k0, %2}";
6884 return "add{l}\t{%2, %k0|%k0, %2}";
6888 (if_then_else (match_operand:SI 2 "incdec_operand" "")
6889 (const_string "incdec")
6890 (const_string "alu")))
6891 (set_attr "mode" "SI")])
6893 (define_insn "*addsi_3"
6894 [(set (reg FLAGS_REG)
6895 (compare (neg:SI (match_operand:SI 2 "general_operand" "g"))
6896 (match_operand:SI 1 "nonimmediate_operand" "%0")))
6897 (clobber (match_scratch:SI 0 "=r"))]
6898 "ix86_match_ccmode (insn, CCZmode)
6899 && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6900 /* Current assemblers are broken and do not allow @GOTOFF in
6901 ought but a memory context. */
6902 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6904 switch (get_attr_type (insn))
6907 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6908 if (operands[2] == const1_rtx)
6909 return "inc{l}\t%0";
6912 gcc_assert (operands[2] == constm1_rtx);
6913 return "dec{l}\t%0";
6917 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6918 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6919 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6920 if (CONST_INT_P (operands[2])
6921 && (INTVAL (operands[2]) == 128
6922 || (INTVAL (operands[2]) < 0
6923 && INTVAL (operands[2]) != -128)))
6925 operands[2] = GEN_INT (-INTVAL (operands[2]));
6926 return "sub{l}\t{%2, %0|%0, %2}";
6928 return "add{l}\t{%2, %0|%0, %2}";
6932 (if_then_else (match_operand:SI 2 "incdec_operand" "")
6933 (const_string "incdec")
6934 (const_string "alu")))
6935 (set_attr "mode" "SI")])
6937 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6938 (define_insn "*addsi_3_zext"
6939 [(set (reg FLAGS_REG)
6940 (compare (neg:SI (match_operand:SI 2 "general_operand" "g"))
6941 (match_operand:SI 1 "nonimmediate_operand" "%0")))
6942 (set (match_operand:DI 0 "register_operand" "=r")
6943 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6944 "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
6945 && ix86_binary_operator_ok (PLUS, SImode, operands)
6946 /* Current assemblers are broken and do not allow @GOTOFF in
6947 ought but a memory context. */
6948 && ! pic_symbolic_operand (operands[2], VOIDmode)"
6950 switch (get_attr_type (insn))
6953 if (operands[2] == const1_rtx)
6954 return "inc{l}\t%k0";
6957 gcc_assert (operands[2] == constm1_rtx);
6958 return "dec{l}\t%k0";
6962 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6963 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6964 if (CONST_INT_P (operands[2])
6965 && (INTVAL (operands[2]) == 128
6966 || (INTVAL (operands[2]) < 0
6967 && INTVAL (operands[2]) != -128)))
6969 operands[2] = GEN_INT (-INTVAL (operands[2]));
6970 return "sub{l}\t{%2, %k0|%k0, %2}";
6972 return "add{l}\t{%2, %k0|%k0, %2}";
6976 (if_then_else (match_operand:SI 2 "incdec_operand" "")
6977 (const_string "incdec")
6978 (const_string "alu")))
6979 (set_attr "mode" "SI")])
6981 ; For comparisons against 1, -1 and 128, we may generate better code
6982 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
6983 ; is matched then. We can't accept general immediate, because for
6984 ; case of overflows, the result is messed up.
6985 ; This pattern also don't hold of 0x80000000, since the value overflows
6987 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6988 ; only for comparisons not depending on it.
6989 (define_insn "*addsi_4"
6990 [(set (reg FLAGS_REG)
6991 (compare (match_operand:SI 1 "nonimmediate_operand" "0")
6992 (match_operand:SI 2 "const_int_operand" "n")))
6993 (clobber (match_scratch:SI 0 "=rm"))]
6994 "ix86_match_ccmode (insn, CCGCmode)
6995 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
6997 switch (get_attr_type (insn))
7000 if (operands[2] == constm1_rtx)
7001 return "inc{l}\t%0";
7004 gcc_assert (operands[2] == const1_rtx);
7005 return "dec{l}\t%0";
7009 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7010 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7011 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7012 if ((INTVAL (operands[2]) == -128
7013 || (INTVAL (operands[2]) > 0
7014 && INTVAL (operands[2]) != 128)))
7015 return "sub{l}\t{%2, %0|%0, %2}";
7016 operands[2] = GEN_INT (-INTVAL (operands[2]));
7017 return "add{l}\t{%2, %0|%0, %2}";
7021 (if_then_else (match_operand:SI 2 "incdec_operand" "")
7022 (const_string "incdec")
7023 (const_string "alu")))
7024 (set_attr "mode" "SI")])
7026 (define_insn "*addsi_5"
7027 [(set (reg FLAGS_REG)
7029 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7030 (match_operand:SI 2 "general_operand" "g"))
7032 (clobber (match_scratch:SI 0 "=r"))]
7033 "ix86_match_ccmode (insn, CCGOCmode)
7034 && !(MEM_P (operands[1]) && MEM_P (operands[2]))
7035 /* Current assemblers are broken and do not allow @GOTOFF in
7036 ought but a memory context. */
7037 && ! pic_symbolic_operand (operands[2], VOIDmode)"
7039 switch (get_attr_type (insn))
7042 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7043 if (operands[2] == const1_rtx)
7044 return "inc{l}\t%0";
7047 gcc_assert (operands[2] == constm1_rtx);
7048 return "dec{l}\t%0";
7052 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7053 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7054 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7055 if (CONST_INT_P (operands[2])
7056 && (INTVAL (operands[2]) == 128
7057 || (INTVAL (operands[2]) < 0
7058 && INTVAL (operands[2]) != -128)))
7060 operands[2] = GEN_INT (-INTVAL (operands[2]));
7061 return "sub{l}\t{%2, %0|%0, %2}";
7063 return "add{l}\t{%2, %0|%0, %2}";
7067 (if_then_else (match_operand:SI 2 "incdec_operand" "")
7068 (const_string "incdec")
7069 (const_string "alu")))
7070 (set_attr "mode" "SI")])
7072 (define_expand "addhi3"
7073 [(set (match_operand:HI 0 "nonimmediate_operand" "")
7074 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
7075 (match_operand:HI 2 "general_operand" "")))]
7076 "TARGET_HIMODE_MATH"
7077 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
7079 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
7080 ;; type optimizations enabled by define-splits. This is not important
7081 ;; for PII, and in fact harmful because of partial register stalls.
7083 (define_insn "*addhi_1_lea"
7084 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
7085 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
7086 (match_operand:HI 2 "general_operand" "rn,rm,ln")))
7087 (clobber (reg:CC FLAGS_REG))]
7088 "!TARGET_PARTIAL_REG_STALL
7089 && ix86_binary_operator_ok (PLUS, HImode, operands)"
7091 switch (get_attr_type (insn))
7096 if (operands[2] == const1_rtx)
7097 return "inc{w}\t%0";
7100 gcc_assert (operands[2] == constm1_rtx);
7101 return "dec{w}\t%0";
7105 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7106 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7107 if (CONST_INT_P (operands[2])
7108 && (INTVAL (operands[2]) == 128
7109 || (INTVAL (operands[2]) < 0
7110 && INTVAL (operands[2]) != -128)))
7112 operands[2] = GEN_INT (-INTVAL (operands[2]));
7113 return "sub{w}\t{%2, %0|%0, %2}";
7115 return "add{w}\t{%2, %0|%0, %2}";
7119 (if_then_else (eq_attr "alternative" "2")
7120 (const_string "lea")
7121 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7122 (const_string "incdec")
7123 (const_string "alu"))))
7124 (set_attr "mode" "HI,HI,SI")])
7126 (define_insn "*addhi_1"
7127 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7128 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7129 (match_operand:HI 2 "general_operand" "rn,rm")))
7130 (clobber (reg:CC FLAGS_REG))]
7131 "TARGET_PARTIAL_REG_STALL
7132 && ix86_binary_operator_ok (PLUS, HImode, operands)"
7134 switch (get_attr_type (insn))
7137 if (operands[2] == const1_rtx)
7138 return "inc{w}\t%0";
7141 gcc_assert (operands[2] == constm1_rtx);
7142 return "dec{w}\t%0";
7146 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7147 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7148 if (CONST_INT_P (operands[2])
7149 && (INTVAL (operands[2]) == 128
7150 || (INTVAL (operands[2]) < 0
7151 && INTVAL (operands[2]) != -128)))
7153 operands[2] = GEN_INT (-INTVAL (operands[2]));
7154 return "sub{w}\t{%2, %0|%0, %2}";
7156 return "add{w}\t{%2, %0|%0, %2}";
7160 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7161 (const_string "incdec")
7162 (const_string "alu")))
7163 (set_attr "mode" "HI")])
7165 (define_insn "*addhi_2"
7166 [(set (reg FLAGS_REG)
7168 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7169 (match_operand:HI 2 "general_operand" "rmn,rn"))
7171 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
7172 (plus:HI (match_dup 1) (match_dup 2)))]
7173 "ix86_match_ccmode (insn, CCGOCmode)
7174 && ix86_binary_operator_ok (PLUS, HImode, operands)"
7176 switch (get_attr_type (insn))
7179 if (operands[2] == const1_rtx)
7180 return "inc{w}\t%0";
7183 gcc_assert (operands[2] == constm1_rtx);
7184 return "dec{w}\t%0";
7188 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7189 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7190 if (CONST_INT_P (operands[2])
7191 && (INTVAL (operands[2]) == 128
7192 || (INTVAL (operands[2]) < 0
7193 && INTVAL (operands[2]) != -128)))
7195 operands[2] = GEN_INT (-INTVAL (operands[2]));
7196 return "sub{w}\t{%2, %0|%0, %2}";
7198 return "add{w}\t{%2, %0|%0, %2}";
7202 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7203 (const_string "incdec")
7204 (const_string "alu")))
7205 (set_attr "mode" "HI")])
7207 (define_insn "*addhi_3"
7208 [(set (reg FLAGS_REG)
7209 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmn"))
7210 (match_operand:HI 1 "nonimmediate_operand" "%0")))
7211 (clobber (match_scratch:HI 0 "=r"))]
7212 "ix86_match_ccmode (insn, CCZmode)
7213 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7215 switch (get_attr_type (insn))
7218 if (operands[2] == const1_rtx)
7219 return "inc{w}\t%0";
7222 gcc_assert (operands[2] == constm1_rtx);
7223 return "dec{w}\t%0";
7227 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7228 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7229 if (CONST_INT_P (operands[2])
7230 && (INTVAL (operands[2]) == 128
7231 || (INTVAL (operands[2]) < 0
7232 && INTVAL (operands[2]) != -128)))
7234 operands[2] = GEN_INT (-INTVAL (operands[2]));
7235 return "sub{w}\t{%2, %0|%0, %2}";
7237 return "add{w}\t{%2, %0|%0, %2}";
7241 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7242 (const_string "incdec")
7243 (const_string "alu")))
7244 (set_attr "mode" "HI")])
7246 ; See comments above addsi_4 for details.
7247 (define_insn "*addhi_4"
7248 [(set (reg FLAGS_REG)
7249 (compare (match_operand:HI 1 "nonimmediate_operand" "0")
7250 (match_operand:HI 2 "const_int_operand" "n")))
7251 (clobber (match_scratch:HI 0 "=rm"))]
7252 "ix86_match_ccmode (insn, CCGCmode)
7253 && (INTVAL (operands[2]) & 0xffff) != 0x8000"
7255 switch (get_attr_type (insn))
7258 if (operands[2] == constm1_rtx)
7259 return "inc{w}\t%0";
7262 gcc_assert (operands[2] == const1_rtx);
7263 return "dec{w}\t%0";
7267 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7268 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7269 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7270 if ((INTVAL (operands[2]) == -128
7271 || (INTVAL (operands[2]) > 0
7272 && INTVAL (operands[2]) != 128)))
7273 return "sub{w}\t{%2, %0|%0, %2}";
7274 operands[2] = GEN_INT (-INTVAL (operands[2]));
7275 return "add{w}\t{%2, %0|%0, %2}";
7279 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7280 (const_string "incdec")
7281 (const_string "alu")))
7282 (set_attr "mode" "SI")])
7285 (define_insn "*addhi_5"
7286 [(set (reg FLAGS_REG)
7288 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
7289 (match_operand:HI 2 "general_operand" "rmn"))
7291 (clobber (match_scratch:HI 0 "=r"))]
7292 "ix86_match_ccmode (insn, CCGOCmode)
7293 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7295 switch (get_attr_type (insn))
7298 if (operands[2] == const1_rtx)
7299 return "inc{w}\t%0";
7302 gcc_assert (operands[2] == constm1_rtx);
7303 return "dec{w}\t%0";
7307 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7308 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7309 if (CONST_INT_P (operands[2])
7310 && (INTVAL (operands[2]) == 128
7311 || (INTVAL (operands[2]) < 0
7312 && INTVAL (operands[2]) != -128)))
7314 operands[2] = GEN_INT (-INTVAL (operands[2]));
7315 return "sub{w}\t{%2, %0|%0, %2}";
7317 return "add{w}\t{%2, %0|%0, %2}";
7321 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7322 (const_string "incdec")
7323 (const_string "alu")))
7324 (set_attr "mode" "HI")])
7326 (define_expand "addqi3"
7327 [(set (match_operand:QI 0 "nonimmediate_operand" "")
7328 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
7329 (match_operand:QI 2 "general_operand" "")))]
7330 "TARGET_QIMODE_MATH"
7331 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
7333 ;; %%% Potential partial reg stall on alternative 2. What to do?
7334 (define_insn "*addqi_1_lea"
7335 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
7336 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
7337 (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
7338 (clobber (reg:CC FLAGS_REG))]
7339 "!TARGET_PARTIAL_REG_STALL
7340 && ix86_binary_operator_ok (PLUS, QImode, operands)"
7342 int widen = (which_alternative == 2);
7343 switch (get_attr_type (insn))
7348 if (operands[2] == const1_rtx)
7349 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
7352 gcc_assert (operands[2] == constm1_rtx);
7353 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
7357 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7358 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7359 if (CONST_INT_P (operands[2])
7360 && (INTVAL (operands[2]) == 128
7361 || (INTVAL (operands[2]) < 0
7362 && INTVAL (operands[2]) != -128)))
7364 operands[2] = GEN_INT (-INTVAL (operands[2]));
7366 return "sub{l}\t{%2, %k0|%k0, %2}";
7368 return "sub{b}\t{%2, %0|%0, %2}";
7371 return "add{l}\t{%k2, %k0|%k0, %k2}";
7373 return "add{b}\t{%2, %0|%0, %2}";
7377 (if_then_else (eq_attr "alternative" "3")
7378 (const_string "lea")
7379 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7380 (const_string "incdec")
7381 (const_string "alu"))))
7382 (set_attr "mode" "QI,QI,SI,SI")])
7384 (define_insn "*addqi_1"
7385 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
7386 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7387 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
7388 (clobber (reg:CC FLAGS_REG))]
7389 "TARGET_PARTIAL_REG_STALL
7390 && ix86_binary_operator_ok (PLUS, QImode, operands)"
7392 int widen = (which_alternative == 2);
7393 switch (get_attr_type (insn))
7396 if (operands[2] == const1_rtx)
7397 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
7400 gcc_assert (operands[2] == constm1_rtx);
7401 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
7405 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
7406 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
7407 if (CONST_INT_P (operands[2])
7408 && (INTVAL (operands[2]) == 128
7409 || (INTVAL (operands[2]) < 0
7410 && INTVAL (operands[2]) != -128)))
7412 operands[2] = GEN_INT (-INTVAL (operands[2]));
7414 return "sub{l}\t{%2, %k0|%k0, %2}";
7416 return "sub{b}\t{%2, %0|%0, %2}";
7419 return "add{l}\t{%k2, %k0|%k0, %k2}";
7421 return "add{b}\t{%2, %0|%0, %2}";
7425 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7426 (const_string "incdec")
7427 (const_string "alu")))
7428 (set_attr "mode" "QI,QI,SI")])
7430 (define_insn "*addqi_1_slp"
7431 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7432 (plus:QI (match_dup 0)
7433 (match_operand:QI 1 "general_operand" "qn,qnm")))
7434 (clobber (reg:CC FLAGS_REG))]
7435 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7436 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7438 switch (get_attr_type (insn))
7441 if (operands[1] == const1_rtx)
7442 return "inc{b}\t%0";
7445 gcc_assert (operands[1] == constm1_rtx);
7446 return "dec{b}\t%0";
7450 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. */
7451 if (CONST_INT_P (operands[1])
7452 && INTVAL (operands[1]) < 0)
7454 operands[1] = GEN_INT (-INTVAL (operands[1]));
7455 return "sub{b}\t{%1, %0|%0, %1}";
7457 return "add{b}\t{%1, %0|%0, %1}";
7461 (if_then_else (match_operand:QI 1 "incdec_operand" "")
7462 (const_string "incdec")
7463 (const_string "alu1")))
7464 (set (attr "memory")
7465 (if_then_else (match_operand 1 "memory_operand" "")
7466 (const_string "load")
7467 (const_string "none")))
7468 (set_attr "mode" "QI")])
7470 (define_insn "*addqi_2"
7471 [(set (reg FLAGS_REG)
7473 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
7474 (match_operand:QI 2 "general_operand" "qmn,qn"))
7476 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
7477 (plus:QI (match_dup 1) (match_dup 2)))]
7478 "ix86_match_ccmode (insn, CCGOCmode)
7479 && ix86_binary_operator_ok (PLUS, QImode, operands)"
7481 switch (get_attr_type (insn))
7484 if (operands[2] == const1_rtx)
7485 return "inc{b}\t%0";
7488 gcc_assert (operands[2] == constm1_rtx
7489 || (CONST_INT_P (operands[2])
7490 && INTVAL (operands[2]) == 255));
7491 return "dec{b}\t%0";
7495 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
7496 if (CONST_INT_P (operands[2])
7497 && INTVAL (operands[2]) < 0)
7499 operands[2] = GEN_INT (-INTVAL (operands[2]));
7500 return "sub{b}\t{%2, %0|%0, %2}";
7502 return "add{b}\t{%2, %0|%0, %2}";
7506 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7507 (const_string "incdec")
7508 (const_string "alu")))
7509 (set_attr "mode" "QI")])
7511 (define_insn "*addqi_3"
7512 [(set (reg FLAGS_REG)
7513 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmn"))
7514 (match_operand:QI 1 "nonimmediate_operand" "%0")))
7515 (clobber (match_scratch:QI 0 "=q"))]
7516 "ix86_match_ccmode (insn, CCZmode)
7517 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7519 switch (get_attr_type (insn))
7522 if (operands[2] == const1_rtx)
7523 return "inc{b}\t%0";
7526 gcc_assert (operands[2] == constm1_rtx
7527 || (CONST_INT_P (operands[2])
7528 && INTVAL (operands[2]) == 255));
7529 return "dec{b}\t%0";
7533 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
7534 if (CONST_INT_P (operands[2])
7535 && INTVAL (operands[2]) < 0)
7537 operands[2] = GEN_INT (-INTVAL (operands[2]));
7538 return "sub{b}\t{%2, %0|%0, %2}";
7540 return "add{b}\t{%2, %0|%0, %2}";
7544 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7545 (const_string "incdec")
7546 (const_string "alu")))
7547 (set_attr "mode" "QI")])
7549 ; See comments above addsi_4 for details.
7550 (define_insn "*addqi_4"
7551 [(set (reg FLAGS_REG)
7552 (compare (match_operand:QI 1 "nonimmediate_operand" "0")
7553 (match_operand:QI 2 "const_int_operand" "n")))
7554 (clobber (match_scratch:QI 0 "=qm"))]
7555 "ix86_match_ccmode (insn, CCGCmode)
7556 && (INTVAL (operands[2]) & 0xff) != 0x80"
7558 switch (get_attr_type (insn))
7561 if (operands[2] == constm1_rtx
7562 || (CONST_INT_P (operands[2])
7563 && INTVAL (operands[2]) == 255))
7564 return "inc{b}\t%0";
7567 gcc_assert (operands[2] == const1_rtx);
7568 return "dec{b}\t%0";
7572 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7573 if (INTVAL (operands[2]) < 0)
7575 operands[2] = GEN_INT (-INTVAL (operands[2]));
7576 return "add{b}\t{%2, %0|%0, %2}";
7578 return "sub{b}\t{%2, %0|%0, %2}";
7582 (if_then_else (match_operand:HI 2 "incdec_operand" "")
7583 (const_string "incdec")
7584 (const_string "alu")))
7585 (set_attr "mode" "QI")])
7588 (define_insn "*addqi_5"
7589 [(set (reg FLAGS_REG)
7591 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7592 (match_operand:QI 2 "general_operand" "qmn"))
7594 (clobber (match_scratch:QI 0 "=q"))]
7595 "ix86_match_ccmode (insn, CCGOCmode)
7596 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7598 switch (get_attr_type (insn))
7601 if (operands[2] == const1_rtx)
7602 return "inc{b}\t%0";
7605 gcc_assert (operands[2] == constm1_rtx
7606 || (CONST_INT_P (operands[2])
7607 && INTVAL (operands[2]) == 255));
7608 return "dec{b}\t%0";
7612 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
7613 if (CONST_INT_P (operands[2])
7614 && INTVAL (operands[2]) < 0)
7616 operands[2] = GEN_INT (-INTVAL (operands[2]));
7617 return "sub{b}\t{%2, %0|%0, %2}";
7619 return "add{b}\t{%2, %0|%0, %2}";
7623 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7624 (const_string "incdec")
7625 (const_string "alu")))
7626 (set_attr "mode" "QI")])
7629 (define_insn "addqi_ext_1"
7630 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7635 (match_operand 1 "ext_register_operand" "0")
7638 (match_operand:QI 2 "general_operand" "Qmn")))
7639 (clobber (reg:CC FLAGS_REG))]
7642 switch (get_attr_type (insn))
7645 if (operands[2] == const1_rtx)
7646 return "inc{b}\t%h0";
7649 gcc_assert (operands[2] == constm1_rtx
7650 || (CONST_INT_P (operands[2])
7651 && INTVAL (operands[2]) == 255));
7652 return "dec{b}\t%h0";
7656 return "add{b}\t{%2, %h0|%h0, %2}";
7660 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7661 (const_string "incdec")
7662 (const_string "alu")))
7663 (set_attr "mode" "QI")])
7665 (define_insn "*addqi_ext_1_rex64"
7666 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7671 (match_operand 1 "ext_register_operand" "0")
7674 (match_operand:QI 2 "nonmemory_operand" "Qn")))
7675 (clobber (reg:CC FLAGS_REG))]
7678 switch (get_attr_type (insn))
7681 if (operands[2] == const1_rtx)
7682 return "inc{b}\t%h0";
7685 gcc_assert (operands[2] == constm1_rtx
7686 || (CONST_INT_P (operands[2])
7687 && INTVAL (operands[2]) == 255));
7688 return "dec{b}\t%h0";
7692 return "add{b}\t{%2, %h0|%h0, %2}";
7696 (if_then_else (match_operand:QI 2 "incdec_operand" "")
7697 (const_string "incdec")
7698 (const_string "alu")))
7699 (set_attr "mode" "QI")])
7701 (define_insn "*addqi_ext_2"
7702 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7707 (match_operand 1 "ext_register_operand" "%0")
7711 (match_operand 2 "ext_register_operand" "Q")
7714 (clobber (reg:CC FLAGS_REG))]
7716 "add{b}\t{%h2, %h0|%h0, %h2}"
7717 [(set_attr "type" "alu")
7718 (set_attr "mode" "QI")])
7720 ;; The patterns that match these are at the end of this file.
7722 (define_expand "addxf3"
7723 [(set (match_operand:XF 0 "register_operand" "")
7724 (plus:XF (match_operand:XF 1 "register_operand" "")
7725 (match_operand:XF 2 "register_operand" "")))]
7729 (define_expand "add<mode>3"
7730 [(set (match_operand:MODEF 0 "register_operand" "")
7731 (plus:MODEF (match_operand:MODEF 1 "register_operand" "")
7732 (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7733 "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
7734 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
7737 ;; Subtract instructions
7739 ;; %%% splits for subditi3
7741 (define_expand "subti3"
7742 [(set (match_operand:TI 0 "nonimmediate_operand" "")
7743 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7744 (match_operand:TI 2 "x86_64_general_operand" "")))]
7746 "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;")
7748 (define_insn "*subti3_1"
7749 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
7750 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0")
7751 (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
7752 (clobber (reg:CC FLAGS_REG))]
7753 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)"
7757 [(set (match_operand:TI 0 "nonimmediate_operand" "")
7758 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7759 (match_operand:TI 2 "x86_64_general_operand" "")))
7760 (clobber (reg:CC FLAGS_REG))]
7761 "TARGET_64BIT && reload_completed"
7762 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7763 (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))])
7764 (parallel [(set (match_dup 3)
7765 (minus:DI (match_dup 4)
7766 (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
7768 (clobber (reg:CC FLAGS_REG))])]
7769 "split_ti (&operands[0], 3, &operands[0], &operands[3]);")
7771 ;; %%% splits for subsidi3
7773 (define_expand "subdi3"
7774 [(set (match_operand:DI 0 "nonimmediate_operand" "")
7775 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7776 (match_operand:DI 2 "x86_64_general_operand" "")))]
7778 "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
7780 (define_insn "*subdi3_1"
7781 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
7782 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7783 (match_operand:DI 2 "general_operand" "roiF,riF")))
7784 (clobber (reg:CC FLAGS_REG))]
7785 "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7789 [(set (match_operand:DI 0 "nonimmediate_operand" "")
7790 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7791 (match_operand:DI 2 "general_operand" "")))
7792 (clobber (reg:CC FLAGS_REG))]
7793 "!TARGET_64BIT && reload_completed"
7794 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7795 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
7796 (parallel [(set (match_dup 3)
7797 (minus:SI (match_dup 4)
7798 (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
7800 (clobber (reg:CC FLAGS_REG))])]
7801 "split_di (&operands[0], 3, &operands[0], &operands[3]);")
7803 (define_insn "subdi3_carry_rex64"
7804 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7805 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7806 (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
7807 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
7808 (clobber (reg:CC FLAGS_REG))]
7809 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7810 "sbb{q}\t{%2, %0|%0, %2}"
7811 [(set_attr "type" "alu")
7812 (set_attr "use_carry" "1")
7813 (set_attr "pent_pair" "pu")
7814 (set_attr "mode" "DI")])
7816 (define_insn "*subdi_1_rex64"
7817 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7818 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7819 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7820 (clobber (reg:CC FLAGS_REG))]
7821 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7822 "sub{q}\t{%2, %0|%0, %2}"
7823 [(set_attr "type" "alu")
7824 (set_attr "mode" "DI")])
7826 (define_insn "*subdi_2_rex64"
7827 [(set (reg FLAGS_REG)
7829 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7830 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
7832 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7833 (minus:DI (match_dup 1) (match_dup 2)))]
7834 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7835 && ix86_binary_operator_ok (MINUS, DImode, operands)"
7836 "sub{q}\t{%2, %0|%0, %2}"
7837 [(set_attr "type" "alu")
7838 (set_attr "mode" "DI")])
7840 (define_insn "*subdi_3_rex63"
7841 [(set (reg FLAGS_REG)
7842 (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
7843 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7844 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7845 (minus:DI (match_dup 1) (match_dup 2)))]
7846 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7847 && ix86_binary_operator_ok (MINUS, SImode, operands)"
7848 "sub{q}\t{%2, %0|%0, %2}"
7849 [(set_attr "type" "alu")
7850 (set_attr "mode" "DI")])
7852 (define_insn "subqi3_carry"
7853 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
7854 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7855 (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
7856 (match_operand:QI 2 "general_operand" "qn,qm"))))
7857 (clobber (reg:CC FLAGS_REG))]
7858 "ix86_binary_operator_ok (MINUS, QImode, operands)"
7859 "sbb{b}\t{%2, %0|%0, %2}"
7860 [(set_attr "type" "alu")
7861 (set_attr "use_carry" "1")
7862 (set_attr "pent_pair" "pu")
7863 (set_attr "mode" "QI")])
7865 (define_insn "subhi3_carry"
7866 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7867 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7868 (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
7869 (match_operand:HI 2 "general_operand" "rn,rm"))))
7870 (clobber (reg:CC FLAGS_REG))]
7871 "ix86_binary_operator_ok (MINUS, HImode, operands)"
7872 "sbb{w}\t{%2, %0|%0, %2}"
7873 [(set_attr "type" "alu")
7874 (set_attr "use_carry" "1")
7875 (set_attr "pent_pair" "pu")
7876 (set_attr "mode" "HI")])
7878 (define_insn "subsi3_carry"
7879 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7880 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7881 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7882 (match_operand:SI 2 "general_operand" "ri,rm"))))
7883 (clobber (reg:CC FLAGS_REG))]
7884 "ix86_binary_operator_ok (MINUS, SImode, operands)"
7885 "sbb{l}\t{%2, %0|%0, %2}"
7886 [(set_attr "type" "alu")
7887 (set_attr "use_carry" "1")
7888 (set_attr "pent_pair" "pu")
7889 (set_attr "mode" "SI")])
7891 (define_insn "subsi3_carry_zext"
7892 [(set (match_operand:DI 0 "register_operand" "=r")
7894 (minus:SI (match_operand:SI 1 "register_operand" "0")
7895 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7896 (match_operand:SI 2 "general_operand" "g")))))
7897 (clobber (reg:CC FLAGS_REG))]
7898 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7899 "sbb{l}\t{%2, %k0|%k0, %2}"
7900 [(set_attr "type" "alu")
7901 (set_attr "pent_pair" "pu")
7902 (set_attr "mode" "SI")])
7904 (define_expand "subsi3"
7905 [(set (match_operand:SI 0 "nonimmediate_operand" "")
7906 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
7907 (match_operand:SI 2 "general_operand" "")))]
7909 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
7911 (define_insn "*subsi_1"
7912 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7913 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7914 (match_operand:SI 2 "general_operand" "ri,rm")))
7915 (clobber (reg:CC FLAGS_REG))]
7916 "ix86_binary_operator_ok (MINUS, SImode, operands)"
7917 "sub{l}\t{%2, %0|%0, %2}"
7918 [(set_attr "type" "alu")
7919 (set_attr "mode" "SI")])
7921 (define_insn "*subsi_1_zext"
7922 [(set (match_operand:DI 0 "register_operand" "=r")
7924 (minus:SI (match_operand:SI 1 "register_operand" "0")
7925 (match_operand:SI 2 "general_operand" "g"))))
7926 (clobber (reg:CC FLAGS_REG))]
7927 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7928 "sub{l}\t{%2, %k0|%k0, %2}"
7929 [(set_attr "type" "alu")
7930 (set_attr "mode" "SI")])
7932 (define_insn "*subsi_2"
7933 [(set (reg FLAGS_REG)
7935 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7936 (match_operand:SI 2 "general_operand" "ri,rm"))
7938 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7939 (minus:SI (match_dup 1) (match_dup 2)))]
7940 "ix86_match_ccmode (insn, CCGOCmode)
7941 && ix86_binary_operator_ok (MINUS, SImode, operands)"
7942 "sub{l}\t{%2, %0|%0, %2}"
7943 [(set_attr "type" "alu")
7944 (set_attr "mode" "SI")])
7946 (define_insn "*subsi_2_zext"
7947 [(set (reg FLAGS_REG)
7949 (minus:SI (match_operand:SI 1 "register_operand" "0")
7950 (match_operand:SI 2 "general_operand" "g"))
7952 (set (match_operand:DI 0 "register_operand" "=r")
7954 (minus:SI (match_dup 1)
7956 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7957 && ix86_binary_operator_ok (MINUS, SImode, operands)"
7958 "sub{l}\t{%2, %k0|%k0, %2}"
7959 [(set_attr "type" "alu")
7960 (set_attr "mode" "SI")])
7962 (define_insn "*subsi_3"
7963 [(set (reg FLAGS_REG)
7964 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
7965 (match_operand:SI 2 "general_operand" "ri,rm")))
7966 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7967 (minus:SI (match_dup 1) (match_dup 2)))]
7968 "ix86_match_ccmode (insn, CCmode)
7969 && ix86_binary_operator_ok (MINUS, SImode, operands)"
7970 "sub{l}\t{%2, %0|%0, %2}"
7971 [(set_attr "type" "alu")
7972 (set_attr "mode" "SI")])
7974 (define_insn "*subsi_3_zext"
7975 [(set (reg FLAGS_REG)
7976 (compare (match_operand:SI 1 "register_operand" "0")
7977 (match_operand:SI 2 "general_operand" "g")))
7978 (set (match_operand:DI 0 "register_operand" "=r")
7980 (minus:SI (match_dup 1)
7982 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7983 && ix86_binary_operator_ok (MINUS, SImode, operands)"
7984 "sub{l}\t{%2, %1|%1, %2}"
7985 [(set_attr "type" "alu")
7986 (set_attr "mode" "DI")])
7988 (define_expand "subhi3"
7989 [(set (match_operand:HI 0 "nonimmediate_operand" "")
7990 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
7991 (match_operand:HI 2 "general_operand" "")))]
7992 "TARGET_HIMODE_MATH"
7993 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
7995 (define_insn "*subhi_1"
7996 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7997 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7998 (match_operand:HI 2 "general_operand" "rn,rm")))
7999 (clobber (reg:CC FLAGS_REG))]
8000 "ix86_binary_operator_ok (MINUS, HImode, operands)"
8001 "sub{w}\t{%2, %0|%0, %2}"
8002 [(set_attr "type" "alu")
8003 (set_attr "mode" "HI")])
8005 (define_insn "*subhi_2"
8006 [(set (reg FLAGS_REG)
8008 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
8009 (match_operand:HI 2 "general_operand" "rn,rm"))
8011 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
8012 (minus:HI (match_dup 1) (match_dup 2)))]
8013 "ix86_match_ccmode (insn, CCGOCmode)
8014 && ix86_binary_operator_ok (MINUS, HImode, operands)"
8015 "sub{w}\t{%2, %0|%0, %2}"
8016 [(set_attr "type" "alu")
8017 (set_attr "mode" "HI")])
8019 (define_insn "*subhi_3"
8020 [(set (reg FLAGS_REG)
8021 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
8022 (match_operand:HI 2 "general_operand" "rn,rm")))
8023 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
8024 (minus:HI (match_dup 1) (match_dup 2)))]
8025 "ix86_match_ccmode (insn, CCmode)
8026 && ix86_binary_operator_ok (MINUS, HImode, operands)"
8027 "sub{w}\t{%2, %0|%0, %2}"
8028 [(set_attr "type" "alu")
8029 (set_attr "mode" "HI")])
8031 (define_expand "subqi3"
8032 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8033 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
8034 (match_operand:QI 2 "general_operand" "")))]
8035 "TARGET_QIMODE_MATH"
8036 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
8038 (define_insn "*subqi_1"
8039 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
8040 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
8041 (match_operand:QI 2 "general_operand" "qn,qm")))
8042 (clobber (reg:CC FLAGS_REG))]
8043 "ix86_binary_operator_ok (MINUS, QImode, operands)"
8044 "sub{b}\t{%2, %0|%0, %2}"
8045 [(set_attr "type" "alu")
8046 (set_attr "mode" "QI")])
8048 (define_insn "*subqi_1_slp"
8049 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8050 (minus:QI (match_dup 0)
8051 (match_operand:QI 1 "general_operand" "qn,qm")))
8052 (clobber (reg:CC FLAGS_REG))]
8053 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8054 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8055 "sub{b}\t{%1, %0|%0, %1}"
8056 [(set_attr "type" "alu1")
8057 (set_attr "mode" "QI")])
8059 (define_insn "*subqi_2"
8060 [(set (reg FLAGS_REG)
8062 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
8063 (match_operand:QI 2 "general_operand" "qn,qm"))
8065 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
8066 (minus:QI (match_dup 1) (match_dup 2)))]
8067 "ix86_match_ccmode (insn, CCGOCmode)
8068 && ix86_binary_operator_ok (MINUS, QImode, operands)"
8069 "sub{b}\t{%2, %0|%0, %2}"
8070 [(set_attr "type" "alu")
8071 (set_attr "mode" "QI")])
8073 (define_insn "*subqi_3"
8074 [(set (reg FLAGS_REG)
8075 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
8076 (match_operand:QI 2 "general_operand" "qn,qm")))
8077 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
8078 (minus:QI (match_dup 1) (match_dup 2)))]
8079 "ix86_match_ccmode (insn, CCmode)
8080 && ix86_binary_operator_ok (MINUS, QImode, operands)"
8081 "sub{b}\t{%2, %0|%0, %2}"
8082 [(set_attr "type" "alu")
8083 (set_attr "mode" "QI")])
8085 ;; The patterns that match these are at the end of this file.
8087 (define_expand "subxf3"
8088 [(set (match_operand:XF 0 "register_operand" "")
8089 (minus:XF (match_operand:XF 1 "register_operand" "")
8090 (match_operand:XF 2 "register_operand" "")))]
8094 (define_expand "sub<mode>3"
8095 [(set (match_operand:MODEF 0 "register_operand" "")
8096 (minus:MODEF (match_operand:MODEF 1 "register_operand" "")
8097 (match_operand:MODEF 2 "nonimmediate_operand" "")))]
8098 "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
8099 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8102 ;; Multiply instructions
8104 (define_expand "muldi3"
8105 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8106 (mult:DI (match_operand:DI 1 "register_operand" "")
8107 (match_operand:DI 2 "x86_64_general_operand" "")))
8108 (clobber (reg:CC FLAGS_REG))])]
8113 ;; IMUL reg64, reg64, imm8 Direct
8114 ;; IMUL reg64, mem64, imm8 VectorPath
8115 ;; IMUL reg64, reg64, imm32 Direct
8116 ;; IMUL reg64, mem64, imm32 VectorPath
8117 ;; IMUL reg64, reg64 Direct
8118 ;; IMUL reg64, mem64 Direct
8120 (define_insn "*muldi3_1_rex64"
8121 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
8122 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
8123 (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
8124 (clobber (reg:CC FLAGS_REG))]
8126 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8128 imul{q}\t{%2, %1, %0|%0, %1, %2}
8129 imul{q}\t{%2, %1, %0|%0, %1, %2}
8130 imul{q}\t{%2, %0|%0, %2}"
8131 [(set_attr "type" "imul")
8132 (set_attr "prefix_0f" "0,0,1")
8133 (set (attr "athlon_decode")
8134 (cond [(eq_attr "cpu" "athlon")
8135 (const_string "vector")
8136 (eq_attr "alternative" "1")
8137 (const_string "vector")
8138 (and (eq_attr "alternative" "2")
8139 (match_operand 1 "memory_operand" ""))
8140 (const_string "vector")]
8141 (const_string "direct")))
8142 (set (attr "amdfam10_decode")
8143 (cond [(and (eq_attr "alternative" "0,1")
8144 (match_operand 1 "memory_operand" ""))
8145 (const_string "vector")]
8146 (const_string "direct")))
8147 (set_attr "mode" "DI")])
8149 (define_expand "mulsi3"
8150 [(parallel [(set (match_operand:SI 0 "register_operand" "")
8151 (mult:SI (match_operand:SI 1 "register_operand" "")
8152 (match_operand:SI 2 "general_operand" "")))
8153 (clobber (reg:CC FLAGS_REG))])]
8158 ;; IMUL reg32, reg32, imm8 Direct
8159 ;; IMUL reg32, mem32, imm8 VectorPath
8160 ;; IMUL reg32, reg32, imm32 Direct
8161 ;; IMUL reg32, mem32, imm32 VectorPath
8162 ;; IMUL reg32, reg32 Direct
8163 ;; IMUL reg32, mem32 Direct
8165 (define_insn "*mulsi3_1"
8166 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
8167 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
8168 (match_operand:SI 2 "general_operand" "K,i,mr")))
8169 (clobber (reg:CC FLAGS_REG))]
8170 "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8172 imul{l}\t{%2, %1, %0|%0, %1, %2}
8173 imul{l}\t{%2, %1, %0|%0, %1, %2}
8174 imul{l}\t{%2, %0|%0, %2}"
8175 [(set_attr "type" "imul")
8176 (set_attr "prefix_0f" "0,0,1")
8177 (set (attr "athlon_decode")
8178 (cond [(eq_attr "cpu" "athlon")
8179 (const_string "vector")
8180 (eq_attr "alternative" "1")
8181 (const_string "vector")
8182 (and (eq_attr "alternative" "2")
8183 (match_operand 1 "memory_operand" ""))
8184 (const_string "vector")]
8185 (const_string "direct")))
8186 (set (attr "amdfam10_decode")
8187 (cond [(and (eq_attr "alternative" "0,1")
8188 (match_operand 1 "memory_operand" ""))
8189 (const_string "vector")]
8190 (const_string "direct")))
8191 (set_attr "mode" "SI")])
8193 (define_insn "*mulsi3_1_zext"
8194 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
8196 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
8197 (match_operand:SI 2 "general_operand" "K,i,mr"))))
8198 (clobber (reg:CC FLAGS_REG))]
8200 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8202 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
8203 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
8204 imul{l}\t{%2, %k0|%k0, %2}"
8205 [(set_attr "type" "imul")
8206 (set_attr "prefix_0f" "0,0,1")
8207 (set (attr "athlon_decode")
8208 (cond [(eq_attr "cpu" "athlon")
8209 (const_string "vector")
8210 (eq_attr "alternative" "1")
8211 (const_string "vector")
8212 (and (eq_attr "alternative" "2")
8213 (match_operand 1 "memory_operand" ""))
8214 (const_string "vector")]
8215 (const_string "direct")))
8216 (set (attr "amdfam10_decode")
8217 (cond [(and (eq_attr "alternative" "0,1")
8218 (match_operand 1 "memory_operand" ""))
8219 (const_string "vector")]
8220 (const_string "direct")))
8221 (set_attr "mode" "SI")])
8223 (define_expand "mulhi3"
8224 [(parallel [(set (match_operand:HI 0 "register_operand" "")
8225 (mult:HI (match_operand:HI 1 "register_operand" "")
8226 (match_operand:HI 2 "general_operand" "")))
8227 (clobber (reg:CC FLAGS_REG))])]
8228 "TARGET_HIMODE_MATH"
8232 ;; IMUL reg16, reg16, imm8 VectorPath
8233 ;; IMUL reg16, mem16, imm8 VectorPath
8234 ;; IMUL reg16, reg16, imm16 VectorPath
8235 ;; IMUL reg16, mem16, imm16 VectorPath
8236 ;; IMUL reg16, reg16 Direct
8237 ;; IMUL reg16, mem16 Direct
8238 (define_insn "*mulhi3_1"
8239 [(set (match_operand:HI 0 "register_operand" "=r,r,r")
8240 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
8241 (match_operand:HI 2 "general_operand" "K,n,mr")))
8242 (clobber (reg:CC FLAGS_REG))]
8243 "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8245 imul{w}\t{%2, %1, %0|%0, %1, %2}
8246 imul{w}\t{%2, %1, %0|%0, %1, %2}
8247 imul{w}\t{%2, %0|%0, %2}"
8248 [(set_attr "type" "imul")
8249 (set_attr "prefix_0f" "0,0,1")
8250 (set (attr "athlon_decode")
8251 (cond [(eq_attr "cpu" "athlon")
8252 (const_string "vector")
8253 (eq_attr "alternative" "1,2")
8254 (const_string "vector")]
8255 (const_string "direct")))
8256 (set (attr "amdfam10_decode")
8257 (cond [(eq_attr "alternative" "0,1")
8258 (const_string "vector")]
8259 (const_string "direct")))
8260 (set_attr "mode" "HI")])
8262 (define_expand "mulqi3"
8263 [(parallel [(set (match_operand:QI 0 "register_operand" "")
8264 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
8265 (match_operand:QI 2 "register_operand" "")))
8266 (clobber (reg:CC FLAGS_REG))])]
8267 "TARGET_QIMODE_MATH"
8274 (define_insn "*mulqi3_1"
8275 [(set (match_operand:QI 0 "register_operand" "=a")
8276 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8277 (match_operand:QI 2 "nonimmediate_operand" "qm")))
8278 (clobber (reg:CC FLAGS_REG))]
8280 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8282 [(set_attr "type" "imul")
8283 (set_attr "length_immediate" "0")
8284 (set (attr "athlon_decode")
8285 (if_then_else (eq_attr "cpu" "athlon")
8286 (const_string "vector")
8287 (const_string "direct")))
8288 (set_attr "amdfam10_decode" "direct")
8289 (set_attr "mode" "QI")])
8291 (define_expand "umulqihi3"
8292 [(parallel [(set (match_operand:HI 0 "register_operand" "")
8293 (mult:HI (zero_extend:HI
8294 (match_operand:QI 1 "nonimmediate_operand" ""))
8296 (match_operand:QI 2 "register_operand" ""))))
8297 (clobber (reg:CC FLAGS_REG))])]
8298 "TARGET_QIMODE_MATH"
8301 (define_insn "*umulqihi3_1"
8302 [(set (match_operand:HI 0 "register_operand" "=a")
8303 (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
8304 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
8305 (clobber (reg:CC FLAGS_REG))]
8307 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8309 [(set_attr "type" "imul")
8310 (set_attr "length_immediate" "0")
8311 (set (attr "athlon_decode")
8312 (if_then_else (eq_attr "cpu" "athlon")
8313 (const_string "vector")
8314 (const_string "direct")))
8315 (set_attr "amdfam10_decode" "direct")
8316 (set_attr "mode" "QI")])
8318 (define_expand "mulqihi3"
8319 [(parallel [(set (match_operand:HI 0 "register_operand" "")
8320 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
8321 (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
8322 (clobber (reg:CC FLAGS_REG))])]
8323 "TARGET_QIMODE_MATH"
8326 (define_insn "*mulqihi3_insn"
8327 [(set (match_operand:HI 0 "register_operand" "=a")
8328 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
8329 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
8330 (clobber (reg:CC FLAGS_REG))]
8332 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8334 [(set_attr "type" "imul")
8335 (set_attr "length_immediate" "0")
8336 (set (attr "athlon_decode")
8337 (if_then_else (eq_attr "cpu" "athlon")
8338 (const_string "vector")
8339 (const_string "direct")))
8340 (set_attr "amdfam10_decode" "direct")
8341 (set_attr "mode" "QI")])
8343 (define_expand "umulditi3"
8344 [(parallel [(set (match_operand:TI 0 "register_operand" "")
8345 (mult:TI (zero_extend:TI
8346 (match_operand:DI 1 "nonimmediate_operand" ""))
8348 (match_operand:DI 2 "register_operand" ""))))
8349 (clobber (reg:CC FLAGS_REG))])]
8353 (define_insn "*umulditi3_insn"
8354 [(set (match_operand:TI 0 "register_operand" "=A")
8355 (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
8356 (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
8357 (clobber (reg:CC FLAGS_REG))]
8359 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8361 [(set_attr "type" "imul")
8362 (set_attr "length_immediate" "0")
8363 (set (attr "athlon_decode")
8364 (if_then_else (eq_attr "cpu" "athlon")
8365 (const_string "vector")
8366 (const_string "double")))
8367 (set_attr "amdfam10_decode" "double")
8368 (set_attr "mode" "DI")])
8370 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
8371 (define_expand "umulsidi3"
8372 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8373 (mult:DI (zero_extend:DI
8374 (match_operand:SI 1 "nonimmediate_operand" ""))
8376 (match_operand:SI 2 "register_operand" ""))))
8377 (clobber (reg:CC FLAGS_REG))])]
8381 (define_insn "*umulsidi3_insn"
8382 [(set (match_operand:DI 0 "register_operand" "=A")
8383 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
8384 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
8385 (clobber (reg:CC FLAGS_REG))]
8387 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8389 [(set_attr "type" "imul")
8390 (set_attr "length_immediate" "0")
8391 (set (attr "athlon_decode")
8392 (if_then_else (eq_attr "cpu" "athlon")
8393 (const_string "vector")
8394 (const_string "double")))
8395 (set_attr "amdfam10_decode" "double")
8396 (set_attr "mode" "SI")])
8398 (define_expand "mulditi3"
8399 [(parallel [(set (match_operand:TI 0 "register_operand" "")
8400 (mult:TI (sign_extend:TI
8401 (match_operand:DI 1 "nonimmediate_operand" ""))
8403 (match_operand:DI 2 "register_operand" ""))))
8404 (clobber (reg:CC FLAGS_REG))])]
8408 (define_insn "*mulditi3_insn"
8409 [(set (match_operand:TI 0 "register_operand" "=A")
8410 (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
8411 (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
8412 (clobber (reg:CC FLAGS_REG))]
8414 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8416 [(set_attr "type" "imul")
8417 (set_attr "length_immediate" "0")
8418 (set (attr "athlon_decode")
8419 (if_then_else (eq_attr "cpu" "athlon")
8420 (const_string "vector")
8421 (const_string "double")))
8422 (set_attr "amdfam10_decode" "double")
8423 (set_attr "mode" "DI")])
8425 (define_expand "mulsidi3"
8426 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8427 (mult:DI (sign_extend:DI
8428 (match_operand:SI 1 "nonimmediate_operand" ""))
8430 (match_operand:SI 2 "register_operand" ""))))
8431 (clobber (reg:CC FLAGS_REG))])]
8435 (define_insn "*mulsidi3_insn"
8436 [(set (match_operand:DI 0 "register_operand" "=A")
8437 (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
8438 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
8439 (clobber (reg:CC FLAGS_REG))]
8441 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8443 [(set_attr "type" "imul")
8444 (set_attr "length_immediate" "0")
8445 (set (attr "athlon_decode")
8446 (if_then_else (eq_attr "cpu" "athlon")
8447 (const_string "vector")
8448 (const_string "double")))
8449 (set_attr "amdfam10_decode" "double")
8450 (set_attr "mode" "SI")])
8452 (define_expand "umuldi3_highpart"
8453 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8456 (mult:TI (zero_extend:TI
8457 (match_operand:DI 1 "nonimmediate_operand" ""))
8459 (match_operand:DI 2 "register_operand" "")))
8461 (clobber (match_scratch:DI 3 ""))
8462 (clobber (reg:CC FLAGS_REG))])]
8466 (define_insn "*umuldi3_highpart_rex64"
8467 [(set (match_operand:DI 0 "register_operand" "=d")
8470 (mult:TI (zero_extend:TI
8471 (match_operand:DI 1 "nonimmediate_operand" "%a"))
8473 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8475 (clobber (match_scratch:DI 3 "=1"))
8476 (clobber (reg:CC FLAGS_REG))]
8478 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8480 [(set_attr "type" "imul")
8481 (set_attr "length_immediate" "0")
8482 (set (attr "athlon_decode")
8483 (if_then_else (eq_attr "cpu" "athlon")
8484 (const_string "vector")
8485 (const_string "double")))
8486 (set_attr "amdfam10_decode" "double")
8487 (set_attr "mode" "DI")])
8489 (define_expand "umulsi3_highpart"
8490 [(parallel [(set (match_operand:SI 0 "register_operand" "")
8493 (mult:DI (zero_extend:DI
8494 (match_operand:SI 1 "nonimmediate_operand" ""))
8496 (match_operand:SI 2 "register_operand" "")))
8498 (clobber (match_scratch:SI 3 ""))
8499 (clobber (reg:CC FLAGS_REG))])]
8503 (define_insn "*umulsi3_highpart_insn"
8504 [(set (match_operand:SI 0 "register_operand" "=d")
8507 (mult:DI (zero_extend:DI
8508 (match_operand:SI 1 "nonimmediate_operand" "%a"))
8510 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8512 (clobber (match_scratch:SI 3 "=1"))
8513 (clobber (reg:CC FLAGS_REG))]
8514 "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8516 [(set_attr "type" "imul")
8517 (set_attr "length_immediate" "0")
8518 (set (attr "athlon_decode")
8519 (if_then_else (eq_attr "cpu" "athlon")
8520 (const_string "vector")
8521 (const_string "double")))
8522 (set_attr "amdfam10_decode" "double")
8523 (set_attr "mode" "SI")])
8525 (define_insn "*umulsi3_highpart_zext"
8526 [(set (match_operand:DI 0 "register_operand" "=d")
8527 (zero_extend:DI (truncate:SI
8529 (mult:DI (zero_extend:DI
8530 (match_operand:SI 1 "nonimmediate_operand" "%a"))
8532 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8534 (clobber (match_scratch:SI 3 "=1"))
8535 (clobber (reg:CC FLAGS_REG))]
8537 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8539 [(set_attr "type" "imul")
8540 (set_attr "length_immediate" "0")
8541 (set (attr "athlon_decode")
8542 (if_then_else (eq_attr "cpu" "athlon")
8543 (const_string "vector")
8544 (const_string "double")))
8545 (set_attr "amdfam10_decode" "double")
8546 (set_attr "mode" "SI")])
8548 (define_expand "smuldi3_highpart"
8549 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8552 (mult:TI (sign_extend:TI
8553 (match_operand:DI 1 "nonimmediate_operand" ""))
8555 (match_operand:DI 2 "register_operand" "")))
8557 (clobber (match_scratch:DI 3 ""))
8558 (clobber (reg:CC FLAGS_REG))])]
8562 (define_insn "*smuldi3_highpart_rex64"
8563 [(set (match_operand:DI 0 "register_operand" "=d")
8566 (mult:TI (sign_extend:TI
8567 (match_operand:DI 1 "nonimmediate_operand" "%a"))
8569 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8571 (clobber (match_scratch:DI 3 "=1"))
8572 (clobber (reg:CC FLAGS_REG))]
8574 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8576 [(set_attr "type" "imul")
8577 (set (attr "athlon_decode")
8578 (if_then_else (eq_attr "cpu" "athlon")
8579 (const_string "vector")
8580 (const_string "double")))
8581 (set_attr "amdfam10_decode" "double")
8582 (set_attr "mode" "DI")])
8584 (define_expand "smulsi3_highpart"
8585 [(parallel [(set (match_operand:SI 0 "register_operand" "")
8588 (mult:DI (sign_extend:DI
8589 (match_operand:SI 1 "nonimmediate_operand" ""))
8591 (match_operand:SI 2 "register_operand" "")))
8593 (clobber (match_scratch:SI 3 ""))
8594 (clobber (reg:CC FLAGS_REG))])]
8598 (define_insn "*smulsi3_highpart_insn"
8599 [(set (match_operand:SI 0 "register_operand" "=d")
8602 (mult:DI (sign_extend:DI
8603 (match_operand:SI 1 "nonimmediate_operand" "%a"))
8605 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8607 (clobber (match_scratch:SI 3 "=1"))
8608 (clobber (reg:CC FLAGS_REG))]
8609 "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8611 [(set_attr "type" "imul")
8612 (set (attr "athlon_decode")
8613 (if_then_else (eq_attr "cpu" "athlon")
8614 (const_string "vector")
8615 (const_string "double")))
8616 (set_attr "amdfam10_decode" "double")
8617 (set_attr "mode" "SI")])
8619 (define_insn "*smulsi3_highpart_zext"
8620 [(set (match_operand:DI 0 "register_operand" "=d")
8621 (zero_extend:DI (truncate:SI
8623 (mult:DI (sign_extend:DI
8624 (match_operand:SI 1 "nonimmediate_operand" "%a"))
8626 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8628 (clobber (match_scratch:SI 3 "=1"))
8629 (clobber (reg:CC FLAGS_REG))]
8631 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8633 [(set_attr "type" "imul")
8634 (set (attr "athlon_decode")
8635 (if_then_else (eq_attr "cpu" "athlon")
8636 (const_string "vector")
8637 (const_string "double")))
8638 (set_attr "amdfam10_decode" "double")
8639 (set_attr "mode" "SI")])
8641 ;; The patterns that match these are at the end of this file.
8643 (define_expand "mulxf3"
8644 [(set (match_operand:XF 0 "register_operand" "")
8645 (mult:XF (match_operand:XF 1 "register_operand" "")
8646 (match_operand:XF 2 "register_operand" "")))]
8650 (define_expand "mul<mode>3"
8651 [(set (match_operand:MODEF 0 "register_operand" "")
8652 (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
8653 (match_operand:MODEF 2 "nonimmediate_operand" "")))]
8654 "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
8655 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8658 ;; SSE5 scalar multiply/add instructions are defined in sse.md.
8661 ;; Divide instructions
8663 (define_insn "divqi3"
8664 [(set (match_operand:QI 0 "register_operand" "=a")
8665 (div:QI (match_operand:HI 1 "register_operand" "0")
8666 (match_operand:QI 2 "nonimmediate_operand" "qm")))
8667 (clobber (reg:CC FLAGS_REG))]
8668 "TARGET_QIMODE_MATH"
8670 [(set_attr "type" "idiv")
8671 (set_attr "mode" "QI")])
8673 (define_insn "udivqi3"
8674 [(set (match_operand:QI 0 "register_operand" "=a")
8675 (udiv:QI (match_operand:HI 1 "register_operand" "0")
8676 (match_operand:QI 2 "nonimmediate_operand" "qm")))
8677 (clobber (reg:CC FLAGS_REG))]
8678 "TARGET_QIMODE_MATH"
8680 [(set_attr "type" "idiv")
8681 (set_attr "mode" "QI")])
8683 ;; The patterns that match these are at the end of this file.
8685 (define_expand "divxf3"
8686 [(set (match_operand:XF 0 "register_operand" "")
8687 (div:XF (match_operand:XF 1 "register_operand" "")
8688 (match_operand:XF 2 "register_operand" "")))]
8692 (define_expand "divdf3"
8693 [(set (match_operand:DF 0 "register_operand" "")
8694 (div:DF (match_operand:DF 1 "register_operand" "")
8695 (match_operand:DF 2 "nonimmediate_operand" "")))]
8696 "(TARGET_80387 && X87_ENABLE_ARITH (DFmode))
8697 || (TARGET_SSE2 && TARGET_SSE_MATH)"
8700 (define_expand "divsf3"
8701 [(set (match_operand:SF 0 "register_operand" "")
8702 (div:SF (match_operand:SF 1 "register_operand" "")
8703 (match_operand:SF 2 "nonimmediate_operand" "")))]
8704 "(TARGET_80387 && X87_ENABLE_ARITH (SFmode))
8707 if (TARGET_SSE_MATH && TARGET_RECIP && optimize_insn_for_speed_p ()
8708 && flag_finite_math_only && !flag_trapping_math
8709 && flag_unsafe_math_optimizations)
8711 ix86_emit_swdivsf (operands[0], operands[1],
8712 operands[2], SFmode);
8717 ;; Remainder instructions.
8719 (define_expand "divmoddi4"
8720 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8721 (div:DI (match_operand:DI 1 "register_operand" "")
8722 (match_operand:DI 2 "nonimmediate_operand" "")))
8723 (set (match_operand:DI 3 "register_operand" "")
8724 (mod:DI (match_dup 1) (match_dup 2)))
8725 (clobber (reg:CC FLAGS_REG))])]
8729 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8730 ;; Penalize eax case slightly because it results in worse scheduling
8732 (define_insn "*divmoddi4_nocltd_rex64"
8733 [(set (match_operand:DI 0 "register_operand" "=&a,?a")
8734 (div:DI (match_operand:DI 2 "register_operand" "1,0")
8735 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
8736 (set (match_operand:DI 1 "register_operand" "=&d,&d")
8737 (mod:DI (match_dup 2) (match_dup 3)))
8738 (clobber (reg:CC FLAGS_REG))]
8739 "TARGET_64BIT && optimize_function_for_speed_p (cfun) && !TARGET_USE_CLTD"
8741 [(set_attr "type" "multi")])
8743 (define_insn "*divmoddi4_cltd_rex64"
8744 [(set (match_operand:DI 0 "register_operand" "=a")
8745 (div:DI (match_operand:DI 2 "register_operand" "a")
8746 (match_operand:DI 3 "nonimmediate_operand" "rm")))
8747 (set (match_operand:DI 1 "register_operand" "=&d")
8748 (mod:DI (match_dup 2) (match_dup 3)))
8749 (clobber (reg:CC FLAGS_REG))]
8750 "TARGET_64BIT && (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)"
8752 [(set_attr "type" "multi")])
8754 (define_insn "*divmoddi_noext_rex64"
8755 [(set (match_operand:DI 0 "register_operand" "=a")
8756 (div:DI (match_operand:DI 1 "register_operand" "0")
8757 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8758 (set (match_operand:DI 3 "register_operand" "=d")
8759 (mod:DI (match_dup 1) (match_dup 2)))
8760 (use (match_operand:DI 4 "register_operand" "3"))
8761 (clobber (reg:CC FLAGS_REG))]
8764 [(set_attr "type" "idiv")
8765 (set_attr "mode" "DI")])
8768 [(set (match_operand:DI 0 "register_operand" "")
8769 (div:DI (match_operand:DI 1 "register_operand" "")
8770 (match_operand:DI 2 "nonimmediate_operand" "")))
8771 (set (match_operand:DI 3 "register_operand" "")
8772 (mod:DI (match_dup 1) (match_dup 2)))
8773 (clobber (reg:CC FLAGS_REG))]
8774 "TARGET_64BIT && reload_completed"
8775 [(parallel [(set (match_dup 3)
8776 (ashiftrt:DI (match_dup 4) (const_int 63)))
8777 (clobber (reg:CC FLAGS_REG))])
8778 (parallel [(set (match_dup 0)
8779 (div:DI (reg:DI 0) (match_dup 2)))
8781 (mod:DI (reg:DI 0) (match_dup 2)))
8783 (clobber (reg:CC FLAGS_REG))])]
8785 /* Avoid use of cltd in favor of a mov+shift. */
8786 if (!TARGET_USE_CLTD && optimize_function_for_speed_p (cfun))
8788 if (true_regnum (operands[1]))
8789 emit_move_insn (operands[0], operands[1]);
8791 emit_move_insn (operands[3], operands[1]);
8792 operands[4] = operands[3];
8796 gcc_assert (!true_regnum (operands[1]));
8797 operands[4] = operands[1];
8802 (define_expand "divmodsi4"
8803 [(parallel [(set (match_operand:SI 0 "register_operand" "")
8804 (div:SI (match_operand:SI 1 "register_operand" "")
8805 (match_operand:SI 2 "nonimmediate_operand" "")))
8806 (set (match_operand:SI 3 "register_operand" "")
8807 (mod:SI (match_dup 1) (match_dup 2)))
8808 (clobber (reg:CC FLAGS_REG))])]
8812 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8813 ;; Penalize eax case slightly because it results in worse scheduling
8815 (define_insn "*divmodsi4_nocltd"
8816 [(set (match_operand:SI 0 "register_operand" "=&a,?a")
8817 (div:SI (match_operand:SI 2 "register_operand" "1,0")
8818 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
8819 (set (match_operand:SI 1 "register_operand" "=&d,&d")
8820 (mod:SI (match_dup 2) (match_dup 3)))
8821 (clobber (reg:CC FLAGS_REG))]
8822 "optimize_function_for_speed_p (cfun) && !TARGET_USE_CLTD"
8824 [(set_attr "type" "multi")])
8826 (define_insn "*divmodsi4_cltd"
8827 [(set (match_operand:SI 0 "register_operand" "=a")
8828 (div:SI (match_operand:SI 2 "register_operand" "a")
8829 (match_operand:SI 3 "nonimmediate_operand" "rm")))
8830 (set (match_operand:SI 1 "register_operand" "=&d")
8831 (mod:SI (match_dup 2) (match_dup 3)))
8832 (clobber (reg:CC FLAGS_REG))]
8833 "optimize_function_for_size_p (cfun) || TARGET_USE_CLTD"
8835 [(set_attr "type" "multi")])
8837 (define_insn "*divmodsi_noext"
8838 [(set (match_operand:SI 0 "register_operand" "=a")
8839 (div:SI (match_operand:SI 1 "register_operand" "0")
8840 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8841 (set (match_operand:SI 3 "register_operand" "=d")
8842 (mod:SI (match_dup 1) (match_dup 2)))
8843 (use (match_operand:SI 4 "register_operand" "3"))
8844 (clobber (reg:CC FLAGS_REG))]
8847 [(set_attr "type" "idiv")
8848 (set_attr "mode" "SI")])
8851 [(set (match_operand:SI 0 "register_operand" "")
8852 (div:SI (match_operand:SI 1 "register_operand" "")
8853 (match_operand:SI 2 "nonimmediate_operand" "")))
8854 (set (match_operand:SI 3 "register_operand" "")
8855 (mod:SI (match_dup 1) (match_dup 2)))
8856 (clobber (reg:CC FLAGS_REG))]
8858 [(parallel [(set (match_dup 3)
8859 (ashiftrt:SI (match_dup 4) (const_int 31)))
8860 (clobber (reg:CC FLAGS_REG))])
8861 (parallel [(set (match_dup 0)
8862 (div:SI (reg:SI 0) (match_dup 2)))
8864 (mod:SI (reg:SI 0) (match_dup 2)))
8866 (clobber (reg:CC FLAGS_REG))])]
8868 /* Avoid use of cltd in favor of a mov+shift. */
8869 if (!TARGET_USE_CLTD && optimize_function_for_speed_p (cfun))
8871 if (true_regnum (operands[1]))
8872 emit_move_insn (operands[0], operands[1]);
8874 emit_move_insn (operands[3], operands[1]);
8875 operands[4] = operands[3];
8879 gcc_assert (!true_regnum (operands[1]));
8880 operands[4] = operands[1];
8884 (define_insn "divmodhi4"
8885 [(set (match_operand:HI 0 "register_operand" "=a")
8886 (div:HI (match_operand:HI 1 "register_operand" "0")
8887 (match_operand:HI 2 "nonimmediate_operand" "rm")))
8888 (set (match_operand:HI 3 "register_operand" "=&d")
8889 (mod:HI (match_dup 1) (match_dup 2)))
8890 (clobber (reg:CC FLAGS_REG))]
8891 "TARGET_HIMODE_MATH"
8893 [(set_attr "type" "multi")
8894 (set_attr "length_immediate" "0")
8895 (set_attr "mode" "SI")])
8897 (define_insn "udivmoddi4"
8898 [(set (match_operand:DI 0 "register_operand" "=a")
8899 (udiv:DI (match_operand:DI 1 "register_operand" "0")
8900 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8901 (set (match_operand:DI 3 "register_operand" "=&d")
8902 (umod:DI (match_dup 1) (match_dup 2)))
8903 (clobber (reg:CC FLAGS_REG))]
8905 "xor{q}\t%3, %3\;div{q}\t%2"
8906 [(set_attr "type" "multi")
8907 (set_attr "length_immediate" "0")
8908 (set_attr "mode" "DI")])
8910 (define_insn "*udivmoddi4_noext"
8911 [(set (match_operand:DI 0 "register_operand" "=a")
8912 (udiv:DI (match_operand:DI 1 "register_operand" "0")
8913 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8914 (set (match_operand:DI 3 "register_operand" "=d")
8915 (umod:DI (match_dup 1) (match_dup 2)))
8917 (clobber (reg:CC FLAGS_REG))]
8920 [(set_attr "type" "idiv")
8921 (set_attr "mode" "DI")])
8924 [(set (match_operand:DI 0 "register_operand" "")
8925 (udiv:DI (match_operand:DI 1 "register_operand" "")
8926 (match_operand:DI 2 "nonimmediate_operand" "")))
8927 (set (match_operand:DI 3 "register_operand" "")
8928 (umod:DI (match_dup 1) (match_dup 2)))
8929 (clobber (reg:CC FLAGS_REG))]
8930 "TARGET_64BIT && reload_completed"
8931 [(set (match_dup 3) (const_int 0))
8932 (parallel [(set (match_dup 0)
8933 (udiv:DI (match_dup 1) (match_dup 2)))
8935 (umod:DI (match_dup 1) (match_dup 2)))
8937 (clobber (reg:CC FLAGS_REG))])]
8940 (define_insn "udivmodsi4"
8941 [(set (match_operand:SI 0 "register_operand" "=a")
8942 (udiv:SI (match_operand:SI 1 "register_operand" "0")
8943 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8944 (set (match_operand:SI 3 "register_operand" "=&d")
8945 (umod:SI (match_dup 1) (match_dup 2)))
8946 (clobber (reg:CC FLAGS_REG))]
8948 "xor{l}\t%3, %3\;div{l}\t%2"
8949 [(set_attr "type" "multi")
8950 (set_attr "length_immediate" "0")
8951 (set_attr "mode" "SI")])
8953 (define_insn "*udivmodsi4_noext"
8954 [(set (match_operand:SI 0 "register_operand" "=a")
8955 (udiv:SI (match_operand:SI 1 "register_operand" "0")
8956 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8957 (set (match_operand:SI 3 "register_operand" "=d")
8958 (umod:SI (match_dup 1) (match_dup 2)))
8960 (clobber (reg:CC FLAGS_REG))]
8963 [(set_attr "type" "idiv")
8964 (set_attr "mode" "SI")])
8967 [(set (match_operand:SI 0 "register_operand" "")
8968 (udiv:SI (match_operand:SI 1 "register_operand" "")
8969 (match_operand:SI 2 "nonimmediate_operand" "")))
8970 (set (match_operand:SI 3 "register_operand" "")
8971 (umod:SI (match_dup 1) (match_dup 2)))
8972 (clobber (reg:CC FLAGS_REG))]
8974 [(set (match_dup 3) (const_int 0))
8975 (parallel [(set (match_dup 0)
8976 (udiv:SI (match_dup 1) (match_dup 2)))
8978 (umod:SI (match_dup 1) (match_dup 2)))
8980 (clobber (reg:CC FLAGS_REG))])]
8983 (define_expand "udivmodhi4"
8984 [(set (match_dup 4) (const_int 0))
8985 (parallel [(set (match_operand:HI 0 "register_operand" "")
8986 (udiv:HI (match_operand:HI 1 "register_operand" "")
8987 (match_operand:HI 2 "nonimmediate_operand" "")))
8988 (set (match_operand:HI 3 "register_operand" "")
8989 (umod:HI (match_dup 1) (match_dup 2)))
8991 (clobber (reg:CC FLAGS_REG))])]
8992 "TARGET_HIMODE_MATH"
8993 "operands[4] = gen_reg_rtx (HImode);")
8995 (define_insn "*udivmodhi_noext"
8996 [(set (match_operand:HI 0 "register_operand" "=a")
8997 (udiv:HI (match_operand:HI 1 "register_operand" "0")
8998 (match_operand:HI 2 "nonimmediate_operand" "rm")))
8999 (set (match_operand:HI 3 "register_operand" "=d")
9000 (umod:HI (match_dup 1) (match_dup 2)))
9001 (use (match_operand:HI 4 "register_operand" "3"))
9002 (clobber (reg:CC FLAGS_REG))]
9005 [(set_attr "type" "idiv")
9006 (set_attr "mode" "HI")])
9008 ;; We cannot use div/idiv for double division, because it causes
9009 ;; "division by zero" on the overflow and that's not what we expect
9010 ;; from truncate. Because true (non truncating) double division is
9011 ;; never generated, we can't create this insn anyway.
9014 ; [(set (match_operand:SI 0 "register_operand" "=a")
9016 ; (udiv:DI (match_operand:DI 1 "register_operand" "A")
9018 ; (match_operand:SI 2 "nonimmediate_operand" "rm")))))
9019 ; (set (match_operand:SI 3 "register_operand" "=d")
9021 ; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
9022 ; (clobber (reg:CC FLAGS_REG))]
9024 ; "div{l}\t{%2, %0|%0, %2}"
9025 ; [(set_attr "type" "idiv")])
9027 ;;- Logical AND instructions
9029 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
9030 ;; Note that this excludes ah.
9032 (define_insn "*testdi_1_rex64"
9033 [(set (reg FLAGS_REG)
9035 (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
9036 (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
9038 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9039 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9041 test{l}\t{%k1, %k0|%k0, %k1}
9042 test{l}\t{%k1, %k0|%k0, %k1}
9043 test{q}\t{%1, %0|%0, %1}
9044 test{q}\t{%1, %0|%0, %1}
9045 test{q}\t{%1, %0|%0, %1}"
9046 [(set_attr "type" "test")
9047 (set_attr "modrm" "0,1,0,1,1")
9048 (set_attr "mode" "SI,SI,DI,DI,DI")
9049 (set_attr "pent_pair" "uv,np,uv,np,uv")])
9051 (define_insn "testsi_1"
9052 [(set (reg FLAGS_REG)
9054 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
9055 (match_operand:SI 1 "general_operand" "i,i,ri"))
9057 "ix86_match_ccmode (insn, CCNOmode)
9058 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9059 "test{l}\t{%1, %0|%0, %1}"
9060 [(set_attr "type" "test")
9061 (set_attr "modrm" "0,1,1")
9062 (set_attr "mode" "SI")
9063 (set_attr "pent_pair" "uv,np,uv")])
9065 (define_expand "testsi_ccno_1"
9066 [(set (reg:CCNO FLAGS_REG)
9068 (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
9069 (match_operand:SI 1 "nonmemory_operand" ""))
9074 (define_insn "*testhi_1"
9075 [(set (reg FLAGS_REG)
9076 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
9077 (match_operand:HI 1 "general_operand" "n,n,rn"))
9079 "ix86_match_ccmode (insn, CCNOmode)
9080 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9081 "test{w}\t{%1, %0|%0, %1}"
9082 [(set_attr "type" "test")
9083 (set_attr "modrm" "0,1,1")
9084 (set_attr "mode" "HI")
9085 (set_attr "pent_pair" "uv,np,uv")])
9087 (define_expand "testqi_ccz_1"
9088 [(set (reg:CCZ FLAGS_REG)
9089 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
9090 (match_operand:QI 1 "nonmemory_operand" ""))
9095 (define_insn "*testqi_1_maybe_si"
9096 [(set (reg FLAGS_REG)
9099 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
9100 (match_operand:QI 1 "general_operand" "n,n,qn,n"))
9102 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
9103 && ix86_match_ccmode (insn,
9104 CONST_INT_P (operands[1])
9105 && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
9107 if (which_alternative == 3)
9109 if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
9110 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
9111 return "test{l}\t{%1, %k0|%k0, %1}";
9113 return "test{b}\t{%1, %0|%0, %1}";
9115 [(set_attr "type" "test")
9116 (set_attr "modrm" "0,1,1,1")
9117 (set_attr "mode" "QI,QI,QI,SI")
9118 (set_attr "pent_pair" "uv,np,uv,np")])
9120 (define_insn "*testqi_1"
9121 [(set (reg FLAGS_REG)
9124 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
9125 (match_operand:QI 1 "general_operand" "n,n,qn"))
9127 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
9128 && ix86_match_ccmode (insn, CCNOmode)"
9129 "test{b}\t{%1, %0|%0, %1}"
9130 [(set_attr "type" "test")
9131 (set_attr "modrm" "0,1,1")
9132 (set_attr "mode" "QI")
9133 (set_attr "pent_pair" "uv,np,uv")])
9135 (define_expand "testqi_ext_ccno_0"
9136 [(set (reg:CCNO FLAGS_REG)
9140 (match_operand 0 "ext_register_operand" "")
9143 (match_operand 1 "const_int_operand" ""))
9148 (define_insn "*testqi_ext_0"
9149 [(set (reg FLAGS_REG)
9153 (match_operand 0 "ext_register_operand" "Q")
9156 (match_operand 1 "const_int_operand" "n"))
9158 "ix86_match_ccmode (insn, CCNOmode)"
9159 "test{b}\t{%1, %h0|%h0, %1}"
9160 [(set_attr "type" "test")
9161 (set_attr "mode" "QI")
9162 (set_attr "length_immediate" "1")
9163 (set_attr "pent_pair" "np")])
9165 (define_insn "*testqi_ext_1"
9166 [(set (reg FLAGS_REG)
9170 (match_operand 0 "ext_register_operand" "Q")
9174 (match_operand:QI 1 "general_operand" "Qm")))
9176 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9177 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9178 "test{b}\t{%1, %h0|%h0, %1}"
9179 [(set_attr "type" "test")
9180 (set_attr "mode" "QI")])
9182 (define_insn "*testqi_ext_1_rex64"
9183 [(set (reg FLAGS_REG)
9187 (match_operand 0 "ext_register_operand" "Q")
9191 (match_operand:QI 1 "register_operand" "Q")))
9193 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9194 "test{b}\t{%1, %h0|%h0, %1}"
9195 [(set_attr "type" "test")
9196 (set_attr "mode" "QI")])
9198 (define_insn "*testqi_ext_2"
9199 [(set (reg FLAGS_REG)
9203 (match_operand 0 "ext_register_operand" "Q")
9207 (match_operand 1 "ext_register_operand" "Q")
9211 "ix86_match_ccmode (insn, CCNOmode)"
9212 "test{b}\t{%h1, %h0|%h0, %h1}"
9213 [(set_attr "type" "test")
9214 (set_attr "mode" "QI")])
9216 ;; Combine likes to form bit extractions for some tests. Humor it.
9217 (define_insn "*testqi_ext_3"
9218 [(set (reg FLAGS_REG)
9219 (compare (zero_extract:SI
9220 (match_operand 0 "nonimmediate_operand" "rm")
9221 (match_operand:SI 1 "const_int_operand" "")
9222 (match_operand:SI 2 "const_int_operand" ""))
9224 "ix86_match_ccmode (insn, CCNOmode)
9225 && INTVAL (operands[1]) > 0
9226 && INTVAL (operands[2]) >= 0
9227 && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
9228 && (GET_MODE (operands[0]) == SImode
9229 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
9230 || GET_MODE (operands[0]) == HImode
9231 || GET_MODE (operands[0]) == QImode)"
9234 (define_insn "*testqi_ext_3_rex64"
9235 [(set (reg FLAGS_REG)
9236 (compare (zero_extract:DI
9237 (match_operand 0 "nonimmediate_operand" "rm")
9238 (match_operand:DI 1 "const_int_operand" "")
9239 (match_operand:DI 2 "const_int_operand" ""))
9242 && ix86_match_ccmode (insn, CCNOmode)
9243 && INTVAL (operands[1]) > 0
9244 && INTVAL (operands[2]) >= 0
9245 /* Ensure that resulting mask is zero or sign extended operand. */
9246 && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
9247 || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
9248 && INTVAL (operands[1]) > 32))
9249 && (GET_MODE (operands[0]) == SImode
9250 || GET_MODE (operands[0]) == DImode
9251 || GET_MODE (operands[0]) == HImode
9252 || GET_MODE (operands[0]) == QImode)"
9256 [(set (match_operand 0 "flags_reg_operand" "")
9257 (match_operator 1 "compare_operator"
9259 (match_operand 2 "nonimmediate_operand" "")
9260 (match_operand 3 "const_int_operand" "")
9261 (match_operand 4 "const_int_operand" ""))
9263 "ix86_match_ccmode (insn, CCNOmode)"
9264 [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
9266 rtx val = operands[2];
9267 HOST_WIDE_INT len = INTVAL (operands[3]);
9268 HOST_WIDE_INT pos = INTVAL (operands[4]);
9270 enum machine_mode mode, submode;
9272 mode = GET_MODE (val);
9275 /* ??? Combine likes to put non-volatile mem extractions in QImode
9276 no matter the size of the test. So find a mode that works. */
9277 if (! MEM_VOLATILE_P (val))
9279 mode = smallest_mode_for_size (pos + len, MODE_INT);
9280 val = adjust_address (val, mode, 0);
9283 else if (GET_CODE (val) == SUBREG
9284 && (submode = GET_MODE (SUBREG_REG (val)),
9285 GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
9286 && pos + len <= GET_MODE_BITSIZE (submode))
9288 /* Narrow a paradoxical subreg to prevent partial register stalls. */
9290 val = SUBREG_REG (val);
9292 else if (mode == HImode && pos + len <= 8)
9294 /* Small HImode tests can be converted to QImode. */
9296 val = gen_lowpart (QImode, val);
9299 if (len == HOST_BITS_PER_WIDE_INT)
9302 mask = ((HOST_WIDE_INT)1 << len) - 1;
9305 operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
9308 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
9309 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
9310 ;; this is relatively important trick.
9311 ;; Do the conversion only post-reload to avoid limiting of the register class
9314 [(set (match_operand 0 "flags_reg_operand" "")
9315 (match_operator 1 "compare_operator"
9316 [(and (match_operand 2 "register_operand" "")
9317 (match_operand 3 "const_int_operand" ""))
9320 && QI_REG_P (operands[2])
9321 && GET_MODE (operands[2]) != QImode
9322 && ((ix86_match_ccmode (insn, CCZmode)
9323 && !(INTVAL (operands[3]) & ~(255 << 8)))
9324 || (ix86_match_ccmode (insn, CCNOmode)
9325 && !(INTVAL (operands[3]) & ~(127 << 8))))"
9328 [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
9331 "operands[2] = gen_lowpart (SImode, operands[2]);
9332 operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
9335 [(set (match_operand 0 "flags_reg_operand" "")
9336 (match_operator 1 "compare_operator"
9337 [(and (match_operand 2 "nonimmediate_operand" "")
9338 (match_operand 3 "const_int_operand" ""))
9341 && GET_MODE (operands[2]) != QImode
9342 && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
9343 && ((ix86_match_ccmode (insn, CCZmode)
9344 && !(INTVAL (operands[3]) & ~255))
9345 || (ix86_match_ccmode (insn, CCNOmode)
9346 && !(INTVAL (operands[3]) & ~127)))"
9348 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
9350 "operands[2] = gen_lowpart (QImode, operands[2]);
9351 operands[3] = gen_lowpart (QImode, operands[3]);")
9354 ;; %%% This used to optimize known byte-wide and operations to memory,
9355 ;; and sometimes to QImode registers. If this is considered useful,
9356 ;; it should be done with splitters.
9358 (define_expand "anddi3"
9359 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9360 (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
9361 (match_operand:DI 2 "x86_64_szext_general_operand" "")))]
9363 "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
9365 (define_insn "*anddi_1_rex64"
9366 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
9367 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
9368 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
9369 (clobber (reg:CC FLAGS_REG))]
9370 "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
9372 switch (get_attr_type (insn))
9376 enum machine_mode mode;
9378 gcc_assert (CONST_INT_P (operands[2]));
9379 if (INTVAL (operands[2]) == 0xff)
9383 gcc_assert (INTVAL (operands[2]) == 0xffff);
9387 operands[1] = gen_lowpart (mode, operands[1]);
9389 return "movz{bq|x}\t{%1,%0|%0, %1}";
9391 return "movz{wq|x}\t{%1,%0|%0, %1}";
9395 gcc_assert (rtx_equal_p (operands[0], operands[1]));
9396 if (get_attr_mode (insn) == MODE_SI)
9397 return "and{l}\t{%k2, %k0|%k0, %k2}";
9399 return "and{q}\t{%2, %0|%0, %2}";
9402 [(set_attr "type" "alu,alu,alu,imovx")
9403 (set_attr "length_immediate" "*,*,*,0")
9404 (set_attr "mode" "SI,DI,DI,DI")])
9406 (define_insn "*anddi_2"
9407 [(set (reg FLAGS_REG)
9408 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
9409 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
9411 (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
9412 (and:DI (match_dup 1) (match_dup 2)))]
9413 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9414 && ix86_binary_operator_ok (AND, DImode, operands)"
9416 and{l}\t{%k2, %k0|%k0, %k2}
9417 and{q}\t{%2, %0|%0, %2}
9418 and{q}\t{%2, %0|%0, %2}"
9419 [(set_attr "type" "alu")
9420 (set_attr "mode" "SI,DI,DI")])
9422 (define_expand "andsi3"
9423 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9424 (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
9425 (match_operand:SI 2 "general_operand" "")))]
9427 "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
9429 (define_insn "*andsi_1"
9430 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
9431 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
9432 (match_operand:SI 2 "general_operand" "ri,rm,L")))
9433 (clobber (reg:CC FLAGS_REG))]
9434 "ix86_binary_operator_ok (AND, SImode, operands)"
9436 switch (get_attr_type (insn))
9440 enum machine_mode mode;
9442 gcc_assert (CONST_INT_P (operands[2]));
9443 if (INTVAL (operands[2]) == 0xff)
9447 gcc_assert (INTVAL (operands[2]) == 0xffff);
9451 operands[1] = gen_lowpart (mode, operands[1]);
9453 return "movz{bl|x}\t{%1,%0|%0, %1}";
9455 return "movz{wl|x}\t{%1,%0|%0, %1}";
9459 gcc_assert (rtx_equal_p (operands[0], operands[1]));
9460 return "and{l}\t{%2, %0|%0, %2}";
9463 [(set_attr "type" "alu,alu,imovx")
9464 (set_attr "length_immediate" "*,*,0")
9465 (set_attr "mode" "SI")])
9468 [(set (match_operand 0 "register_operand" "")
9470 (const_int -65536)))
9471 (clobber (reg:CC FLAGS_REG))]
9472 "optimize_function_for_size_p (cfun) || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
9473 [(set (strict_low_part (match_dup 1)) (const_int 0))]
9474 "operands[1] = gen_lowpart (HImode, operands[0]);")
9477 [(set (match_operand 0 "ext_register_operand" "")
9480 (clobber (reg:CC FLAGS_REG))]
9481 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_REG_STALL) && reload_completed"
9482 [(set (strict_low_part (match_dup 1)) (const_int 0))]
9483 "operands[1] = gen_lowpart (QImode, operands[0]);")
9486 [(set (match_operand 0 "ext_register_operand" "")
9488 (const_int -65281)))
9489 (clobber (reg:CC FLAGS_REG))]
9490 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_REG_STALL) && reload_completed"
9491 [(parallel [(set (zero_extract:SI (match_dup 0)
9495 (zero_extract:SI (match_dup 0)
9498 (zero_extract:SI (match_dup 0)
9501 (clobber (reg:CC FLAGS_REG))])]
9502 "operands[0] = gen_lowpart (SImode, operands[0]);")
9504 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9505 (define_insn "*andsi_1_zext"
9506 [(set (match_operand:DI 0 "register_operand" "=r")
9508 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9509 (match_operand:SI 2 "general_operand" "g"))))
9510 (clobber (reg:CC FLAGS_REG))]
9511 "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
9512 "and{l}\t{%2, %k0|%k0, %2}"
9513 [(set_attr "type" "alu")
9514 (set_attr "mode" "SI")])
9516 (define_insn "*andsi_2"
9517 [(set (reg FLAGS_REG)
9518 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9519 (match_operand:SI 2 "general_operand" "g,ri"))
9521 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9522 (and:SI (match_dup 1) (match_dup 2)))]
9523 "ix86_match_ccmode (insn, CCNOmode)
9524 && ix86_binary_operator_ok (AND, SImode, operands)"
9525 "and{l}\t{%2, %0|%0, %2}"
9526 [(set_attr "type" "alu")
9527 (set_attr "mode" "SI")])
9529 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9530 (define_insn "*andsi_2_zext"
9531 [(set (reg FLAGS_REG)
9532 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9533 (match_operand:SI 2 "general_operand" "g"))
9535 (set (match_operand:DI 0 "register_operand" "=r")
9536 (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
9537 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9538 && ix86_binary_operator_ok (AND, SImode, operands)"
9539 "and{l}\t{%2, %k0|%k0, %2}"
9540 [(set_attr "type" "alu")
9541 (set_attr "mode" "SI")])
9543 (define_expand "andhi3"
9544 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9545 (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
9546 (match_operand:HI 2 "general_operand" "")))]
9547 "TARGET_HIMODE_MATH"
9548 "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
9550 (define_insn "*andhi_1"
9551 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
9552 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
9553 (match_operand:HI 2 "general_operand" "rn,rm,L")))
9554 (clobber (reg:CC FLAGS_REG))]
9555 "ix86_binary_operator_ok (AND, HImode, operands)"
9557 switch (get_attr_type (insn))
9560 gcc_assert (CONST_INT_P (operands[2]));
9561 gcc_assert (INTVAL (operands[2]) == 0xff);
9562 return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
9565 gcc_assert (rtx_equal_p (operands[0], operands[1]));
9567 return "and{w}\t{%2, %0|%0, %2}";
9570 [(set_attr "type" "alu,alu,imovx")
9571 (set_attr "length_immediate" "*,*,0")
9572 (set_attr "mode" "HI,HI,SI")])
9574 (define_insn "*andhi_2"
9575 [(set (reg FLAGS_REG)
9576 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9577 (match_operand:HI 2 "general_operand" "rmn,rn"))
9579 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9580 (and:HI (match_dup 1) (match_dup 2)))]
9581 "ix86_match_ccmode (insn, CCNOmode)
9582 && ix86_binary_operator_ok (AND, HImode, operands)"
9583 "and{w}\t{%2, %0|%0, %2}"
9584 [(set_attr "type" "alu")
9585 (set_attr "mode" "HI")])
9587 (define_expand "andqi3"
9588 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9589 (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
9590 (match_operand:QI 2 "general_operand" "")))]
9591 "TARGET_QIMODE_MATH"
9592 "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
9594 ;; %%% Potential partial reg stall on alternative 2. What to do?
9595 (define_insn "*andqi_1"
9596 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
9597 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9598 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
9599 (clobber (reg:CC FLAGS_REG))]
9600 "ix86_binary_operator_ok (AND, QImode, operands)"
9602 and{b}\t{%2, %0|%0, %2}
9603 and{b}\t{%2, %0|%0, %2}
9604 and{l}\t{%k2, %k0|%k0, %k2}"
9605 [(set_attr "type" "alu")
9606 (set_attr "mode" "QI,QI,SI")])
9608 (define_insn "*andqi_1_slp"
9609 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9610 (and:QI (match_dup 0)
9611 (match_operand:QI 1 "general_operand" "qn,qmn")))
9612 (clobber (reg:CC FLAGS_REG))]
9613 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
9614 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9615 "and{b}\t{%1, %0|%0, %1}"
9616 [(set_attr "type" "alu1")
9617 (set_attr "mode" "QI")])
9619 (define_insn "*andqi_2_maybe_si"
9620 [(set (reg FLAGS_REG)
9622 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9623 (match_operand:QI 2 "general_operand" "qmn,qn,n"))
9625 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
9626 (and:QI (match_dup 1) (match_dup 2)))]
9627 "ix86_binary_operator_ok (AND, QImode, operands)
9628 && ix86_match_ccmode (insn,
9629 CONST_INT_P (operands[2])
9630 && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
9632 if (which_alternative == 2)
9634 if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
9635 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
9636 return "and{l}\t{%2, %k0|%k0, %2}";
9638 return "and{b}\t{%2, %0|%0, %2}";
9640 [(set_attr "type" "alu")
9641 (set_attr "mode" "QI,QI,SI")])
9643 (define_insn "*andqi_2"
9644 [(set (reg FLAGS_REG)
9646 (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9647 (match_operand:QI 2 "general_operand" "qmn,qn"))
9649 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9650 (and:QI (match_dup 1) (match_dup 2)))]
9651 "ix86_match_ccmode (insn, CCNOmode)
9652 && ix86_binary_operator_ok (AND, QImode, operands)"
9653 "and{b}\t{%2, %0|%0, %2}"
9654 [(set_attr "type" "alu")
9655 (set_attr "mode" "QI")])
9657 (define_insn "*andqi_2_slp"
9658 [(set (reg FLAGS_REG)
9660 (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9661 (match_operand:QI 1 "nonimmediate_operand" "qmn,qn"))
9663 (set (strict_low_part (match_dup 0))
9664 (and:QI (match_dup 0) (match_dup 1)))]
9665 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
9666 && ix86_match_ccmode (insn, CCNOmode)
9667 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9668 "and{b}\t{%1, %0|%0, %1}"
9669 [(set_attr "type" "alu1")
9670 (set_attr "mode" "QI")])
9672 ;; ??? A bug in recog prevents it from recognizing a const_int as an
9673 ;; operand to zero_extend in andqi_ext_1. It was checking explicitly
9674 ;; for a QImode operand, which of course failed.
9676 (define_insn "andqi_ext_0"
9677 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9682 (match_operand 1 "ext_register_operand" "0")
9685 (match_operand 2 "const_int_operand" "n")))
9686 (clobber (reg:CC FLAGS_REG))]
9688 "and{b}\t{%2, %h0|%h0, %2}"
9689 [(set_attr "type" "alu")
9690 (set_attr "length_immediate" "1")
9691 (set_attr "mode" "QI")])
9693 ;; Generated by peephole translating test to and. This shows up
9694 ;; often in fp comparisons.
9696 (define_insn "*andqi_ext_0_cc"
9697 [(set (reg FLAGS_REG)
9701 (match_operand 1 "ext_register_operand" "0")
9704 (match_operand 2 "const_int_operand" "n"))
9706 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9715 "ix86_match_ccmode (insn, CCNOmode)"
9716 "and{b}\t{%2, %h0|%h0, %2}"
9717 [(set_attr "type" "alu")
9718 (set_attr "length_immediate" "1")
9719 (set_attr "mode" "QI")])
9721 (define_insn "*andqi_ext_1"
9722 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9727 (match_operand 1 "ext_register_operand" "0")
9731 (match_operand:QI 2 "general_operand" "Qm"))))
9732 (clobber (reg:CC FLAGS_REG))]
9734 "and{b}\t{%2, %h0|%h0, %2}"
9735 [(set_attr "type" "alu")
9736 (set_attr "length_immediate" "0")
9737 (set_attr "mode" "QI")])
9739 (define_insn "*andqi_ext_1_rex64"
9740 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9745 (match_operand 1 "ext_register_operand" "0")
9749 (match_operand 2 "ext_register_operand" "Q"))))
9750 (clobber (reg:CC FLAGS_REG))]
9752 "and{b}\t{%2, %h0|%h0, %2}"
9753 [(set_attr "type" "alu")
9754 (set_attr "length_immediate" "0")
9755 (set_attr "mode" "QI")])
9757 (define_insn "*andqi_ext_2"
9758 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9763 (match_operand 1 "ext_register_operand" "%0")
9767 (match_operand 2 "ext_register_operand" "Q")
9770 (clobber (reg:CC FLAGS_REG))]
9772 "and{b}\t{%h2, %h0|%h0, %h2}"
9773 [(set_attr "type" "alu")
9774 (set_attr "length_immediate" "0")
9775 (set_attr "mode" "QI")])
9777 ;; Convert wide AND instructions with immediate operand to shorter QImode
9778 ;; equivalents when possible.
9779 ;; Don't do the splitting with memory operands, since it introduces risk
9780 ;; of memory mismatch stalls. We may want to do the splitting for optimizing
9781 ;; for size, but that can (should?) be handled by generic code instead.
9783 [(set (match_operand 0 "register_operand" "")
9784 (and (match_operand 1 "register_operand" "")
9785 (match_operand 2 "const_int_operand" "")))
9786 (clobber (reg:CC FLAGS_REG))]
9788 && QI_REG_P (operands[0])
9789 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
9790 && !(~INTVAL (operands[2]) & ~(255 << 8))
9791 && GET_MODE (operands[0]) != QImode"
9792 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9793 (and:SI (zero_extract:SI (match_dup 1)
9794 (const_int 8) (const_int 8))
9796 (clobber (reg:CC FLAGS_REG))])]
9797 "operands[0] = gen_lowpart (SImode, operands[0]);
9798 operands[1] = gen_lowpart (SImode, operands[1]);
9799 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9801 ;; Since AND can be encoded with sign extended immediate, this is only
9802 ;; profitable when 7th bit is not set.
9804 [(set (match_operand 0 "register_operand" "")
9805 (and (match_operand 1 "general_operand" "")
9806 (match_operand 2 "const_int_operand" "")))
9807 (clobber (reg:CC FLAGS_REG))]
9809 && ANY_QI_REG_P (operands[0])
9810 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
9811 && !(~INTVAL (operands[2]) & ~255)
9812 && !(INTVAL (operands[2]) & 128)
9813 && GET_MODE (operands[0]) != QImode"
9814 [(parallel [(set (strict_low_part (match_dup 0))
9815 (and:QI (match_dup 1)
9817 (clobber (reg:CC FLAGS_REG))])]
9818 "operands[0] = gen_lowpart (QImode, operands[0]);
9819 operands[1] = gen_lowpart (QImode, operands[1]);
9820 operands[2] = gen_lowpart (QImode, operands[2]);")
9822 ;; Logical inclusive OR instructions
9824 ;; %%% This used to optimize known byte-wide and operations to memory.
9825 ;; If this is considered useful, it should be done with splitters.
9827 (define_expand "iordi3"
9828 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9829 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
9830 (match_operand:DI 2 "x86_64_general_operand" "")))]
9832 "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
9834 (define_insn "*iordi_1_rex64"
9835 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9836 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9837 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
9838 (clobber (reg:CC FLAGS_REG))]
9840 && ix86_binary_operator_ok (IOR, DImode, operands)"
9841 "or{q}\t{%2, %0|%0, %2}"
9842 [(set_attr "type" "alu")
9843 (set_attr "mode" "DI")])
9845 (define_insn "*iordi_2_rex64"
9846 [(set (reg FLAGS_REG)
9847 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9848 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9850 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9851 (ior:DI (match_dup 1) (match_dup 2)))]
9853 && ix86_match_ccmode (insn, CCNOmode)
9854 && ix86_binary_operator_ok (IOR, DImode, operands)"
9855 "or{q}\t{%2, %0|%0, %2}"
9856 [(set_attr "type" "alu")
9857 (set_attr "mode" "DI")])
9859 (define_insn "*iordi_3_rex64"
9860 [(set (reg FLAGS_REG)
9861 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9862 (match_operand:DI 2 "x86_64_general_operand" "rem"))
9864 (clobber (match_scratch:DI 0 "=r"))]
9866 && ix86_match_ccmode (insn, CCNOmode)
9867 && ix86_binary_operator_ok (IOR, DImode, operands)"
9868 "or{q}\t{%2, %0|%0, %2}"
9869 [(set_attr "type" "alu")
9870 (set_attr "mode" "DI")])
9873 (define_expand "iorsi3"
9874 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9875 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
9876 (match_operand:SI 2 "general_operand" "")))]
9878 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
9880 (define_insn "*iorsi_1"
9881 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9882 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9883 (match_operand:SI 2 "general_operand" "ri,g")))
9884 (clobber (reg:CC FLAGS_REG))]
9885 "ix86_binary_operator_ok (IOR, SImode, operands)"
9886 "or{l}\t{%2, %0|%0, %2}"
9887 [(set_attr "type" "alu")
9888 (set_attr "mode" "SI")])
9890 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9891 (define_insn "*iorsi_1_zext"
9892 [(set (match_operand:DI 0 "register_operand" "=r")
9894 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9895 (match_operand:SI 2 "general_operand" "g"))))
9896 (clobber (reg:CC FLAGS_REG))]
9897 "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
9898 "or{l}\t{%2, %k0|%k0, %2}"
9899 [(set_attr "type" "alu")
9900 (set_attr "mode" "SI")])
9902 (define_insn "*iorsi_1_zext_imm"
9903 [(set (match_operand:DI 0 "register_operand" "=r")
9904 (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9905 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9906 (clobber (reg:CC FLAGS_REG))]
9908 "or{l}\t{%2, %k0|%k0, %2}"
9909 [(set_attr "type" "alu")
9910 (set_attr "mode" "SI")])
9912 (define_insn "*iorsi_2"
9913 [(set (reg FLAGS_REG)
9914 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9915 (match_operand:SI 2 "general_operand" "g,ri"))
9917 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9918 (ior:SI (match_dup 1) (match_dup 2)))]
9919 "ix86_match_ccmode (insn, CCNOmode)
9920 && ix86_binary_operator_ok (IOR, SImode, operands)"
9921 "or{l}\t{%2, %0|%0, %2}"
9922 [(set_attr "type" "alu")
9923 (set_attr "mode" "SI")])
9925 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9926 ;; ??? Special case for immediate operand is missing - it is tricky.
9927 (define_insn "*iorsi_2_zext"
9928 [(set (reg FLAGS_REG)
9929 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9930 (match_operand:SI 2 "general_operand" "g"))
9932 (set (match_operand:DI 0 "register_operand" "=r")
9933 (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
9934 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9935 && ix86_binary_operator_ok (IOR, SImode, operands)"
9936 "or{l}\t{%2, %k0|%k0, %2}"
9937 [(set_attr "type" "alu")
9938 (set_attr "mode" "SI")])
9940 (define_insn "*iorsi_2_zext_imm"
9941 [(set (reg FLAGS_REG)
9942 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9943 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9945 (set (match_operand:DI 0 "register_operand" "=r")
9946 (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9947 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9948 && ix86_binary_operator_ok (IOR, SImode, operands)"
9949 "or{l}\t{%2, %k0|%k0, %2}"
9950 [(set_attr "type" "alu")
9951 (set_attr "mode" "SI")])
9953 (define_insn "*iorsi_3"
9954 [(set (reg FLAGS_REG)
9955 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9956 (match_operand:SI 2 "general_operand" "g"))
9958 (clobber (match_scratch:SI 0 "=r"))]
9959 "ix86_match_ccmode (insn, CCNOmode)
9960 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9961 "or{l}\t{%2, %0|%0, %2}"
9962 [(set_attr "type" "alu")
9963 (set_attr "mode" "SI")])
9965 (define_expand "iorhi3"
9966 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9967 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
9968 (match_operand:HI 2 "general_operand" "")))]
9969 "TARGET_HIMODE_MATH"
9970 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
9972 (define_insn "*iorhi_1"
9973 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9974 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9975 (match_operand:HI 2 "general_operand" "rmn,rn")))
9976 (clobber (reg:CC FLAGS_REG))]
9977 "ix86_binary_operator_ok (IOR, HImode, operands)"
9978 "or{w}\t{%2, %0|%0, %2}"
9979 [(set_attr "type" "alu")
9980 (set_attr "mode" "HI")])
9982 (define_insn "*iorhi_2"
9983 [(set (reg FLAGS_REG)
9984 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9985 (match_operand:HI 2 "general_operand" "rmn,rn"))
9987 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9988 (ior:HI (match_dup 1) (match_dup 2)))]
9989 "ix86_match_ccmode (insn, CCNOmode)
9990 && ix86_binary_operator_ok (IOR, HImode, operands)"
9991 "or{w}\t{%2, %0|%0, %2}"
9992 [(set_attr "type" "alu")
9993 (set_attr "mode" "HI")])
9995 (define_insn "*iorhi_3"
9996 [(set (reg FLAGS_REG)
9997 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9998 (match_operand:HI 2 "general_operand" "rmn"))
10000 (clobber (match_scratch:HI 0 "=r"))]
10001 "ix86_match_ccmode (insn, CCNOmode)
10002 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10003 "or{w}\t{%2, %0|%0, %2}"
10004 [(set_attr "type" "alu")
10005 (set_attr "mode" "HI")])
10007 (define_expand "iorqi3"
10008 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10009 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
10010 (match_operand:QI 2 "general_operand" "")))]
10011 "TARGET_QIMODE_MATH"
10012 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
10014 ;; %%% Potential partial reg stall on alternative 2. What to do?
10015 (define_insn "*iorqi_1"
10016 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
10017 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
10018 (match_operand:QI 2 "general_operand" "qmn,qn,rn")))
10019 (clobber (reg:CC FLAGS_REG))]
10020 "ix86_binary_operator_ok (IOR, QImode, operands)"
10022 or{b}\t{%2, %0|%0, %2}
10023 or{b}\t{%2, %0|%0, %2}
10024 or{l}\t{%k2, %k0|%k0, %k2}"
10025 [(set_attr "type" "alu")
10026 (set_attr "mode" "QI,QI,SI")])
10028 (define_insn "*iorqi_1_slp"
10029 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
10030 (ior:QI (match_dup 0)
10031 (match_operand:QI 1 "general_operand" "qmn,qn")))
10032 (clobber (reg:CC FLAGS_REG))]
10033 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10034 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
10035 "or{b}\t{%1, %0|%0, %1}"
10036 [(set_attr "type" "alu1")
10037 (set_attr "mode" "QI")])
10039 (define_insn "*iorqi_2"
10040 [(set (reg FLAGS_REG)
10041 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
10042 (match_operand:QI 2 "general_operand" "qmn,qn"))
10044 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
10045 (ior:QI (match_dup 1) (match_dup 2)))]
10046 "ix86_match_ccmode (insn, CCNOmode)
10047 && ix86_binary_operator_ok (IOR, QImode, operands)"
10048 "or{b}\t{%2, %0|%0, %2}"
10049 [(set_attr "type" "alu")
10050 (set_attr "mode" "QI")])
10052 (define_insn "*iorqi_2_slp"
10053 [(set (reg FLAGS_REG)
10054 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
10055 (match_operand:QI 1 "general_operand" "qmn,qn"))
10057 (set (strict_low_part (match_dup 0))
10058 (ior:QI (match_dup 0) (match_dup 1)))]
10059 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10060 && ix86_match_ccmode (insn, CCNOmode)
10061 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
10062 "or{b}\t{%1, %0|%0, %1}"
10063 [(set_attr "type" "alu1")
10064 (set_attr "mode" "QI")])
10066 (define_insn "*iorqi_3"
10067 [(set (reg FLAGS_REG)
10068 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
10069 (match_operand:QI 2 "general_operand" "qmn"))
10071 (clobber (match_scratch:QI 0 "=q"))]
10072 "ix86_match_ccmode (insn, CCNOmode)
10073 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10074 "or{b}\t{%2, %0|%0, %2}"
10075 [(set_attr "type" "alu")
10076 (set_attr "mode" "QI")])
10078 (define_insn "*iorqi_ext_0"
10079 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10084 (match_operand 1 "ext_register_operand" "0")
10087 (match_operand 2 "const_int_operand" "n")))
10088 (clobber (reg:CC FLAGS_REG))]
10089 "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10090 "or{b}\t{%2, %h0|%h0, %2}"
10091 [(set_attr "type" "alu")
10092 (set_attr "length_immediate" "1")
10093 (set_attr "mode" "QI")])
10095 (define_insn "*iorqi_ext_1"
10096 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10101 (match_operand 1 "ext_register_operand" "0")
10105 (match_operand:QI 2 "general_operand" "Qm"))))
10106 (clobber (reg:CC FLAGS_REG))]
10108 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10109 "or{b}\t{%2, %h0|%h0, %2}"
10110 [(set_attr "type" "alu")
10111 (set_attr "length_immediate" "0")
10112 (set_attr "mode" "QI")])
10114 (define_insn "*iorqi_ext_1_rex64"
10115 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10120 (match_operand 1 "ext_register_operand" "0")
10124 (match_operand 2 "ext_register_operand" "Q"))))
10125 (clobber (reg:CC FLAGS_REG))]
10127 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10128 "or{b}\t{%2, %h0|%h0, %2}"
10129 [(set_attr "type" "alu")
10130 (set_attr "length_immediate" "0")
10131 (set_attr "mode" "QI")])
10133 (define_insn "*iorqi_ext_2"
10134 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10138 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
10141 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
10144 (clobber (reg:CC FLAGS_REG))]
10145 "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10146 "ior{b}\t{%h2, %h0|%h0, %h2}"
10147 [(set_attr "type" "alu")
10148 (set_attr "length_immediate" "0")
10149 (set_attr "mode" "QI")])
10152 [(set (match_operand 0 "register_operand" "")
10153 (ior (match_operand 1 "register_operand" "")
10154 (match_operand 2 "const_int_operand" "")))
10155 (clobber (reg:CC FLAGS_REG))]
10157 && QI_REG_P (operands[0])
10158 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10159 && !(INTVAL (operands[2]) & ~(255 << 8))
10160 && GET_MODE (operands[0]) != QImode"
10161 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
10162 (ior:SI (zero_extract:SI (match_dup 1)
10163 (const_int 8) (const_int 8))
10165 (clobber (reg:CC FLAGS_REG))])]
10166 "operands[0] = gen_lowpart (SImode, operands[0]);
10167 operands[1] = gen_lowpart (SImode, operands[1]);
10168 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
10170 ;; Since OR can be encoded with sign extended immediate, this is only
10171 ;; profitable when 7th bit is set.
10173 [(set (match_operand 0 "register_operand" "")
10174 (ior (match_operand 1 "general_operand" "")
10175 (match_operand 2 "const_int_operand" "")))
10176 (clobber (reg:CC FLAGS_REG))]
10178 && ANY_QI_REG_P (operands[0])
10179 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10180 && !(INTVAL (operands[2]) & ~255)
10181 && (INTVAL (operands[2]) & 128)
10182 && GET_MODE (operands[0]) != QImode"
10183 [(parallel [(set (strict_low_part (match_dup 0))
10184 (ior:QI (match_dup 1)
10186 (clobber (reg:CC FLAGS_REG))])]
10187 "operands[0] = gen_lowpart (QImode, operands[0]);
10188 operands[1] = gen_lowpart (QImode, operands[1]);
10189 operands[2] = gen_lowpart (QImode, operands[2]);")
10191 ;; Logical XOR instructions
10193 ;; %%% This used to optimize known byte-wide and operations to memory.
10194 ;; If this is considered useful, it should be done with splitters.
10196 (define_expand "xordi3"
10197 [(set (match_operand:DI 0 "nonimmediate_operand" "")
10198 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
10199 (match_operand:DI 2 "x86_64_general_operand" "")))]
10201 "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
10203 (define_insn "*xordi_1_rex64"
10204 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10205 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
10206 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
10207 (clobber (reg:CC FLAGS_REG))]
10209 && ix86_binary_operator_ok (XOR, DImode, operands)"
10210 "xor{q}\t{%2, %0|%0, %2}"
10211 [(set_attr "type" "alu")
10212 (set_attr "mode" "DI")])
10214 (define_insn "*xordi_2_rex64"
10215 [(set (reg FLAGS_REG)
10216 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
10217 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
10219 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
10220 (xor:DI (match_dup 1) (match_dup 2)))]
10222 && ix86_match_ccmode (insn, CCNOmode)
10223 && ix86_binary_operator_ok (XOR, DImode, operands)"
10224 "xor{q}\t{%2, %0|%0, %2}"
10225 [(set_attr "type" "alu")
10226 (set_attr "mode" "DI")])
10228 (define_insn "*xordi_3_rex64"
10229 [(set (reg FLAGS_REG)
10230 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
10231 (match_operand:DI 2 "x86_64_general_operand" "rem"))
10233 (clobber (match_scratch:DI 0 "=r"))]
10235 && ix86_match_ccmode (insn, CCNOmode)
10236 && ix86_binary_operator_ok (XOR, DImode, operands)"
10237 "xor{q}\t{%2, %0|%0, %2}"
10238 [(set_attr "type" "alu")
10239 (set_attr "mode" "DI")])
10241 (define_expand "xorsi3"
10242 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10243 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
10244 (match_operand:SI 2 "general_operand" "")))]
10246 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
10248 (define_insn "*xorsi_1"
10249 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10250 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
10251 (match_operand:SI 2 "general_operand" "ri,rm")))
10252 (clobber (reg:CC FLAGS_REG))]
10253 "ix86_binary_operator_ok (XOR, SImode, operands)"
10254 "xor{l}\t{%2, %0|%0, %2}"
10255 [(set_attr "type" "alu")
10256 (set_attr "mode" "SI")])
10258 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
10259 ;; Add speccase for immediates
10260 (define_insn "*xorsi_1_zext"
10261 [(set (match_operand:DI 0 "register_operand" "=r")
10263 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
10264 (match_operand:SI 2 "general_operand" "g"))))
10265 (clobber (reg:CC FLAGS_REG))]
10266 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
10267 "xor{l}\t{%2, %k0|%k0, %2}"
10268 [(set_attr "type" "alu")
10269 (set_attr "mode" "SI")])
10271 (define_insn "*xorsi_1_zext_imm"
10272 [(set (match_operand:DI 0 "register_operand" "=r")
10273 (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
10274 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
10275 (clobber (reg:CC FLAGS_REG))]
10276 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
10277 "xor{l}\t{%2, %k0|%k0, %2}"
10278 [(set_attr "type" "alu")
10279 (set_attr "mode" "SI")])
10281 (define_insn "*xorsi_2"
10282 [(set (reg FLAGS_REG)
10283 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
10284 (match_operand:SI 2 "general_operand" "g,ri"))
10286 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
10287 (xor:SI (match_dup 1) (match_dup 2)))]
10288 "ix86_match_ccmode (insn, CCNOmode)
10289 && ix86_binary_operator_ok (XOR, SImode, operands)"
10290 "xor{l}\t{%2, %0|%0, %2}"
10291 [(set_attr "type" "alu")
10292 (set_attr "mode" "SI")])
10294 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
10295 ;; ??? Special case for immediate operand is missing - it is tricky.
10296 (define_insn "*xorsi_2_zext"
10297 [(set (reg FLAGS_REG)
10298 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
10299 (match_operand:SI 2 "general_operand" "g"))
10301 (set (match_operand:DI 0 "register_operand" "=r")
10302 (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
10303 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10304 && ix86_binary_operator_ok (XOR, SImode, operands)"
10305 "xor{l}\t{%2, %k0|%k0, %2}"
10306 [(set_attr "type" "alu")
10307 (set_attr "mode" "SI")])
10309 (define_insn "*xorsi_2_zext_imm"
10310 [(set (reg FLAGS_REG)
10311 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
10312 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
10314 (set (match_operand:DI 0 "register_operand" "=r")
10315 (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
10316 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10317 && ix86_binary_operator_ok (XOR, SImode, operands)"
10318 "xor{l}\t{%2, %k0|%k0, %2}"
10319 [(set_attr "type" "alu")
10320 (set_attr "mode" "SI")])
10322 (define_insn "*xorsi_3"
10323 [(set (reg FLAGS_REG)
10324 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
10325 (match_operand:SI 2 "general_operand" "g"))
10327 (clobber (match_scratch:SI 0 "=r"))]
10328 "ix86_match_ccmode (insn, CCNOmode)
10329 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10330 "xor{l}\t{%2, %0|%0, %2}"
10331 [(set_attr "type" "alu")
10332 (set_attr "mode" "SI")])
10334 (define_expand "xorhi3"
10335 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10336 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
10337 (match_operand:HI 2 "general_operand" "")))]
10338 "TARGET_HIMODE_MATH"
10339 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
10341 (define_insn "*xorhi_1"
10342 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
10343 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
10344 (match_operand:HI 2 "general_operand" "rmn,rn")))
10345 (clobber (reg:CC FLAGS_REG))]
10346 "ix86_binary_operator_ok (XOR, HImode, operands)"
10347 "xor{w}\t{%2, %0|%0, %2}"
10348 [(set_attr "type" "alu")
10349 (set_attr "mode" "HI")])
10351 (define_insn "*xorhi_2"
10352 [(set (reg FLAGS_REG)
10353 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
10354 (match_operand:HI 2 "general_operand" "rmn,rn"))
10356 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
10357 (xor:HI (match_dup 1) (match_dup 2)))]
10358 "ix86_match_ccmode (insn, CCNOmode)
10359 && ix86_binary_operator_ok (XOR, HImode, operands)"
10360 "xor{w}\t{%2, %0|%0, %2}"
10361 [(set_attr "type" "alu")
10362 (set_attr "mode" "HI")])
10364 (define_insn "*xorhi_3"
10365 [(set (reg FLAGS_REG)
10366 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
10367 (match_operand:HI 2 "general_operand" "rmn"))
10369 (clobber (match_scratch:HI 0 "=r"))]
10370 "ix86_match_ccmode (insn, CCNOmode)
10371 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10372 "xor{w}\t{%2, %0|%0, %2}"
10373 [(set_attr "type" "alu")
10374 (set_attr "mode" "HI")])
10376 (define_expand "xorqi3"
10377 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10378 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
10379 (match_operand:QI 2 "general_operand" "")))]
10380 "TARGET_QIMODE_MATH"
10381 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
10383 ;; %%% Potential partial reg stall on alternative 2. What to do?
10384 (define_insn "*xorqi_1"
10385 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
10386 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
10387 (match_operand:QI 2 "general_operand" "qmn,qn,rn")))
10388 (clobber (reg:CC FLAGS_REG))]
10389 "ix86_binary_operator_ok (XOR, QImode, operands)"
10391 xor{b}\t{%2, %0|%0, %2}
10392 xor{b}\t{%2, %0|%0, %2}
10393 xor{l}\t{%k2, %k0|%k0, %k2}"
10394 [(set_attr "type" "alu")
10395 (set_attr "mode" "QI,QI,SI")])
10397 (define_insn "*xorqi_1_slp"
10398 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
10399 (xor:QI (match_dup 0)
10400 (match_operand:QI 1 "general_operand" "qn,qmn")))
10401 (clobber (reg:CC FLAGS_REG))]
10402 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10403 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
10404 "xor{b}\t{%1, %0|%0, %1}"
10405 [(set_attr "type" "alu1")
10406 (set_attr "mode" "QI")])
10408 (define_insn "*xorqi_ext_0"
10409 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10414 (match_operand 1 "ext_register_operand" "0")
10417 (match_operand 2 "const_int_operand" "n")))
10418 (clobber (reg:CC FLAGS_REG))]
10419 "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10420 "xor{b}\t{%2, %h0|%h0, %2}"
10421 [(set_attr "type" "alu")
10422 (set_attr "length_immediate" "1")
10423 (set_attr "mode" "QI")])
10425 (define_insn "*xorqi_ext_1"
10426 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10431 (match_operand 1 "ext_register_operand" "0")
10435 (match_operand:QI 2 "general_operand" "Qm"))))
10436 (clobber (reg:CC FLAGS_REG))]
10438 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10439 "xor{b}\t{%2, %h0|%h0, %2}"
10440 [(set_attr "type" "alu")
10441 (set_attr "length_immediate" "0")
10442 (set_attr "mode" "QI")])
10444 (define_insn "*xorqi_ext_1_rex64"
10445 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10450 (match_operand 1 "ext_register_operand" "0")
10454 (match_operand 2 "ext_register_operand" "Q"))))
10455 (clobber (reg:CC FLAGS_REG))]
10457 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10458 "xor{b}\t{%2, %h0|%h0, %2}"
10459 [(set_attr "type" "alu")
10460 (set_attr "length_immediate" "0")
10461 (set_attr "mode" "QI")])
10463 (define_insn "*xorqi_ext_2"
10464 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10468 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
10471 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
10474 (clobber (reg:CC FLAGS_REG))]
10475 "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
10476 "xor{b}\t{%h2, %h0|%h0, %h2}"
10477 [(set_attr "type" "alu")
10478 (set_attr "length_immediate" "0")
10479 (set_attr "mode" "QI")])
10481 (define_insn "*xorqi_cc_1"
10482 [(set (reg FLAGS_REG)
10484 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
10485 (match_operand:QI 2 "general_operand" "qmn,qn"))
10487 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
10488 (xor:QI (match_dup 1) (match_dup 2)))]
10489 "ix86_match_ccmode (insn, CCNOmode)
10490 && ix86_binary_operator_ok (XOR, QImode, operands)"
10491 "xor{b}\t{%2, %0|%0, %2}"
10492 [(set_attr "type" "alu")
10493 (set_attr "mode" "QI")])
10495 (define_insn "*xorqi_2_slp"
10496 [(set (reg FLAGS_REG)
10497 (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
10498 (match_operand:QI 1 "general_operand" "qmn,qn"))
10500 (set (strict_low_part (match_dup 0))
10501 (xor:QI (match_dup 0) (match_dup 1)))]
10502 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10503 && ix86_match_ccmode (insn, CCNOmode)
10504 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
10505 "xor{b}\t{%1, %0|%0, %1}"
10506 [(set_attr "type" "alu1")
10507 (set_attr "mode" "QI")])
10509 (define_insn "*xorqi_cc_2"
10510 [(set (reg FLAGS_REG)
10512 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
10513 (match_operand:QI 2 "general_operand" "qmn"))
10515 (clobber (match_scratch:QI 0 "=q"))]
10516 "ix86_match_ccmode (insn, CCNOmode)
10517 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10518 "xor{b}\t{%2, %0|%0, %2}"
10519 [(set_attr "type" "alu")
10520 (set_attr "mode" "QI")])
10522 (define_insn "*xorqi_cc_ext_1"
10523 [(set (reg FLAGS_REG)
10527 (match_operand 1 "ext_register_operand" "0")
10530 (match_operand:QI 2 "general_operand" "qmn"))
10532 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
10536 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10538 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10539 "xor{b}\t{%2, %h0|%h0, %2}"
10540 [(set_attr "type" "alu")
10541 (set_attr "mode" "QI")])
10543 (define_insn "*xorqi_cc_ext_1_rex64"
10544 [(set (reg FLAGS_REG)
10548 (match_operand 1 "ext_register_operand" "0")
10551 (match_operand:QI 2 "nonmemory_operand" "Qn"))
10553 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10557 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10559 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10560 "xor{b}\t{%2, %h0|%h0, %2}"
10561 [(set_attr "type" "alu")
10562 (set_attr "mode" "QI")])
10564 (define_expand "xorqi_cc_ext_1"
10566 (set (reg:CCNO FLAGS_REG)
10570 (match_operand 1 "ext_register_operand" "")
10573 (match_operand:QI 2 "general_operand" ""))
10575 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
10579 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10585 [(set (match_operand 0 "register_operand" "")
10586 (xor (match_operand 1 "register_operand" "")
10587 (match_operand 2 "const_int_operand" "")))
10588 (clobber (reg:CC FLAGS_REG))]
10590 && QI_REG_P (operands[0])
10591 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10592 && !(INTVAL (operands[2]) & ~(255 << 8))
10593 && GET_MODE (operands[0]) != QImode"
10594 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
10595 (xor:SI (zero_extract:SI (match_dup 1)
10596 (const_int 8) (const_int 8))
10598 (clobber (reg:CC FLAGS_REG))])]
10599 "operands[0] = gen_lowpart (SImode, operands[0]);
10600 operands[1] = gen_lowpart (SImode, operands[1]);
10601 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
10603 ;; Since XOR can be encoded with sign extended immediate, this is only
10604 ;; profitable when 7th bit is set.
10606 [(set (match_operand 0 "register_operand" "")
10607 (xor (match_operand 1 "general_operand" "")
10608 (match_operand 2 "const_int_operand" "")))
10609 (clobber (reg:CC FLAGS_REG))]
10611 && ANY_QI_REG_P (operands[0])
10612 && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
10613 && !(INTVAL (operands[2]) & ~255)
10614 && (INTVAL (operands[2]) & 128)
10615 && GET_MODE (operands[0]) != QImode"
10616 [(parallel [(set (strict_low_part (match_dup 0))
10617 (xor:QI (match_dup 1)
10619 (clobber (reg:CC FLAGS_REG))])]
10620 "operands[0] = gen_lowpart (QImode, operands[0]);
10621 operands[1] = gen_lowpart (QImode, operands[1]);
10622 operands[2] = gen_lowpart (QImode, operands[2]);")
10624 ;; Negation instructions
10626 (define_expand "negti2"
10627 [(set (match_operand:TI 0 "nonimmediate_operand" "")
10628 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))]
10630 "ix86_expand_unary_operator (NEG, TImode, operands); DONE;")
10632 (define_insn "*negti2_1"
10633 [(set (match_operand:TI 0 "nonimmediate_operand" "=ro")
10634 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "0")))
10635 (clobber (reg:CC FLAGS_REG))]
10637 && ix86_unary_operator_ok (NEG, TImode, operands)"
10641 [(set (match_operand:TI 0 "nonimmediate_operand" "")
10642 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
10643 (clobber (reg:CC FLAGS_REG))]
10644 "TARGET_64BIT && reload_completed"
10646 [(set (reg:CCZ FLAGS_REG)
10647 (compare:CCZ (neg:DI (match_dup 1)) (const_int 0)))
10648 (set (match_dup 0) (neg:DI (match_dup 1)))])
10650 [(set (match_dup 2)
10651 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
10654 (clobber (reg:CC FLAGS_REG))])
10656 [(set (match_dup 2)
10657 (neg:DI (match_dup 2)))
10658 (clobber (reg:CC FLAGS_REG))])]
10659 "split_ti (&operands[0], 2, &operands[0], &operands[2]);")
10661 (define_expand "negdi2"
10662 [(set (match_operand:DI 0 "nonimmediate_operand" "")
10663 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
10665 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
10667 (define_insn "*negdi2_1"
10668 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
10669 (neg:DI (match_operand:DI 1 "general_operand" "0")))
10670 (clobber (reg:CC FLAGS_REG))]
10672 && ix86_unary_operator_ok (NEG, DImode, operands)"
10676 [(set (match_operand:DI 0 "nonimmediate_operand" "")
10677 (neg:DI (match_operand:DI 1 "general_operand" "")))
10678 (clobber (reg:CC FLAGS_REG))]
10679 "!TARGET_64BIT && reload_completed"
10681 [(set (reg:CCZ FLAGS_REG)
10682 (compare:CCZ (neg:SI (match_dup 1)) (const_int 0)))
10683 (set (match_dup 0) (neg:SI (match_dup 1)))])
10685 [(set (match_dup 2)
10686 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
10689 (clobber (reg:CC FLAGS_REG))])
10691 [(set (match_dup 2)
10692 (neg:SI (match_dup 2)))
10693 (clobber (reg:CC FLAGS_REG))])]
10694 "split_di (&operands[0], 2, &operands[0], &operands[2]);");
10696 (define_insn "*negdi2_1_rex64"
10697 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10698 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
10699 (clobber (reg:CC FLAGS_REG))]
10700 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10702 [(set_attr "type" "negnot")
10703 (set_attr "mode" "DI")])
10705 ;; The problem with neg is that it does not perform (compare x 0),
10706 ;; it really performs (compare 0 x), which leaves us with the zero
10707 ;; flag being the only useful item.
10709 (define_insn "*negdi2_cmpz_rex64"
10710 [(set (reg:CCZ FLAGS_REG)
10711 (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10713 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10714 (neg:DI (match_dup 1)))]
10715 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10717 [(set_attr "type" "negnot")
10718 (set_attr "mode" "DI")])
10721 (define_expand "negsi2"
10722 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10723 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10725 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
10727 (define_insn "*negsi2_1"
10728 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10729 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
10730 (clobber (reg:CC FLAGS_REG))]
10731 "ix86_unary_operator_ok (NEG, SImode, operands)"
10733 [(set_attr "type" "negnot")
10734 (set_attr "mode" "SI")])
10736 ;; Combine is quite creative about this pattern.
10737 (define_insn "*negsi2_1_zext"
10738 [(set (match_operand:DI 0 "register_operand" "=r")
10739 (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
10742 (clobber (reg:CC FLAGS_REG))]
10743 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10745 [(set_attr "type" "negnot")
10746 (set_attr "mode" "SI")])
10748 ;; The problem with neg is that it does not perform (compare x 0),
10749 ;; it really performs (compare 0 x), which leaves us with the zero
10750 ;; flag being the only useful item.
10752 (define_insn "*negsi2_cmpz"
10753 [(set (reg:CCZ FLAGS_REG)
10754 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10756 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10757 (neg:SI (match_dup 1)))]
10758 "ix86_unary_operator_ok (NEG, SImode, operands)"
10760 [(set_attr "type" "negnot")
10761 (set_attr "mode" "SI")])
10763 (define_insn "*negsi2_cmpz_zext"
10764 [(set (reg:CCZ FLAGS_REG)
10765 (compare:CCZ (lshiftrt:DI
10767 (match_operand:DI 1 "register_operand" "0")
10771 (set (match_operand:DI 0 "register_operand" "=r")
10772 (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
10775 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10777 [(set_attr "type" "negnot")
10778 (set_attr "mode" "SI")])
10780 (define_expand "neghi2"
10781 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10782 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10783 "TARGET_HIMODE_MATH"
10784 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
10786 (define_insn "*neghi2_1"
10787 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10788 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
10789 (clobber (reg:CC FLAGS_REG))]
10790 "ix86_unary_operator_ok (NEG, HImode, operands)"
10792 [(set_attr "type" "negnot")
10793 (set_attr "mode" "HI")])
10795 (define_insn "*neghi2_cmpz"
10796 [(set (reg:CCZ FLAGS_REG)
10797 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10799 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10800 (neg:HI (match_dup 1)))]
10801 "ix86_unary_operator_ok (NEG, HImode, operands)"
10803 [(set_attr "type" "negnot")
10804 (set_attr "mode" "HI")])
10806 (define_expand "negqi2"
10807 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10808 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10809 "TARGET_QIMODE_MATH"
10810 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
10812 (define_insn "*negqi2_1"
10813 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10814 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
10815 (clobber (reg:CC FLAGS_REG))]
10816 "ix86_unary_operator_ok (NEG, QImode, operands)"
10818 [(set_attr "type" "negnot")
10819 (set_attr "mode" "QI")])
10821 (define_insn "*negqi2_cmpz"
10822 [(set (reg:CCZ FLAGS_REG)
10823 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10825 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10826 (neg:QI (match_dup 1)))]
10827 "ix86_unary_operator_ok (NEG, QImode, operands)"
10829 [(set_attr "type" "negnot")
10830 (set_attr "mode" "QI")])
10832 ;; Changing of sign for FP values is doable using integer unit too.
10834 (define_expand "<code><mode>2"
10835 [(set (match_operand:X87MODEF 0 "register_operand" "")
10836 (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
10837 "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10838 "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
10840 (define_insn "*absneg<mode>2_mixed"
10841 [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
10842 (match_operator:MODEF 3 "absneg_operator"
10843 [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
10844 (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
10845 (clobber (reg:CC FLAGS_REG))]
10846 "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
10849 (define_insn "*absneg<mode>2_sse"
10850 [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
10851 (match_operator:MODEF 3 "absneg_operator"
10852 [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
10853 (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
10854 (clobber (reg:CC FLAGS_REG))]
10855 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
10858 (define_insn "*absneg<mode>2_i387"
10859 [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
10860 (match_operator:X87MODEF 3 "absneg_operator"
10861 [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
10862 (use (match_operand 2 "" ""))
10863 (clobber (reg:CC FLAGS_REG))]
10864 "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10867 (define_expand "<code>tf2"
10868 [(set (match_operand:TF 0 "register_operand" "")
10869 (absneg:TF (match_operand:TF 1 "register_operand" "")))]
10871 "ix86_expand_fp_absneg_operator (<CODE>, TFmode, operands); DONE;")
10873 (define_insn "*absnegtf2_sse"
10874 [(set (match_operand:TF 0 "register_operand" "=x,x")
10875 (match_operator:TF 3 "absneg_operator"
10876 [(match_operand:TF 1 "register_operand" "0,x")]))
10877 (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
10878 (clobber (reg:CC FLAGS_REG))]
10882 ;; Splitters for fp abs and neg.
10885 [(set (match_operand 0 "fp_register_operand" "")
10886 (match_operator 1 "absneg_operator" [(match_dup 0)]))
10887 (use (match_operand 2 "" ""))
10888 (clobber (reg:CC FLAGS_REG))]
10890 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
10893 [(set (match_operand 0 "register_operand" "")
10894 (match_operator 3 "absneg_operator"
10895 [(match_operand 1 "register_operand" "")]))
10896 (use (match_operand 2 "nonimmediate_operand" ""))
10897 (clobber (reg:CC FLAGS_REG))]
10898 "reload_completed && SSE_REG_P (operands[0])"
10899 [(set (match_dup 0) (match_dup 3))]
10901 enum machine_mode mode = GET_MODE (operands[0]);
10902 enum machine_mode vmode = GET_MODE (operands[2]);
10905 operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
10906 operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
10907 if (operands_match_p (operands[0], operands[2]))
10910 operands[1] = operands[2];
10913 if (GET_CODE (operands[3]) == ABS)
10914 tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
10916 tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
10921 [(set (match_operand:SF 0 "register_operand" "")
10922 (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
10923 (use (match_operand:V4SF 2 "" ""))
10924 (clobber (reg:CC FLAGS_REG))]
10926 [(parallel [(set (match_dup 0) (match_dup 1))
10927 (clobber (reg:CC FLAGS_REG))])]
10930 operands[0] = gen_lowpart (SImode, operands[0]);
10931 if (GET_CODE (operands[1]) == ABS)
10933 tmp = gen_int_mode (0x7fffffff, SImode);
10934 tmp = gen_rtx_AND (SImode, operands[0], tmp);
10938 tmp = gen_int_mode (0x80000000, SImode);
10939 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10945 [(set (match_operand:DF 0 "register_operand" "")
10946 (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
10947 (use (match_operand 2 "" ""))
10948 (clobber (reg:CC FLAGS_REG))]
10950 [(parallel [(set (match_dup 0) (match_dup 1))
10951 (clobber (reg:CC FLAGS_REG))])]
10956 tmp = gen_lowpart (DImode, operands[0]);
10957 tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
10960 if (GET_CODE (operands[1]) == ABS)
10963 tmp = gen_rtx_NOT (DImode, tmp);
10967 operands[0] = gen_highpart (SImode, operands[0]);
10968 if (GET_CODE (operands[1]) == ABS)
10970 tmp = gen_int_mode (0x7fffffff, SImode);
10971 tmp = gen_rtx_AND (SImode, operands[0], tmp);
10975 tmp = gen_int_mode (0x80000000, SImode);
10976 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10983 [(set (match_operand:XF 0 "register_operand" "")
10984 (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
10985 (use (match_operand 2 "" ""))
10986 (clobber (reg:CC FLAGS_REG))]
10988 [(parallel [(set (match_dup 0) (match_dup 1))
10989 (clobber (reg:CC FLAGS_REG))])]
10992 operands[0] = gen_rtx_REG (SImode,
10993 true_regnum (operands[0])
10994 + (TARGET_64BIT ? 1 : 2));
10995 if (GET_CODE (operands[1]) == ABS)
10997 tmp = GEN_INT (0x7fff);
10998 tmp = gen_rtx_AND (SImode, operands[0], tmp);
11002 tmp = GEN_INT (0x8000);
11003 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
11008 ;; Conditionalize these after reload. If they match before reload, we
11009 ;; lose the clobber and ability to use integer instructions.
11011 (define_insn "*<code><mode>2_1"
11012 [(set (match_operand:X87MODEF 0 "register_operand" "=f")
11013 (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
11015 && (reload_completed
11016 || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
11018 [(set_attr "type" "fsgn")
11019 (set_attr "mode" "<MODE>")])
11021 (define_insn "*<code>extendsfdf2"
11022 [(set (match_operand:DF 0 "register_operand" "=f")
11023 (absneg:DF (float_extend:DF
11024 (match_operand:SF 1 "register_operand" "0"))))]
11025 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
11027 [(set_attr "type" "fsgn")
11028 (set_attr "mode" "DF")])
11030 (define_insn "*<code>extendsfxf2"
11031 [(set (match_operand:XF 0 "register_operand" "=f")
11032 (absneg:XF (float_extend:XF
11033 (match_operand:SF 1 "register_operand" "0"))))]
11036 [(set_attr "type" "fsgn")
11037 (set_attr "mode" "XF")])
11039 (define_insn "*<code>extenddfxf2"
11040 [(set (match_operand:XF 0 "register_operand" "=f")
11041 (absneg:XF (float_extend:XF
11042 (match_operand:DF 1 "register_operand" "0"))))]
11045 [(set_attr "type" "fsgn")
11046 (set_attr "mode" "XF")])
11048 ;; Copysign instructions
11050 (define_mode_iterator CSGNMODE [SF DF TF])
11051 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
11053 (define_expand "copysign<mode>3"
11054 [(match_operand:CSGNMODE 0 "register_operand" "")
11055 (match_operand:CSGNMODE 1 "nonmemory_operand" "")
11056 (match_operand:CSGNMODE 2 "register_operand" "")]
11057 "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
11058 || (TARGET_SSE2 && (<MODE>mode == TFmode))"
11060 ix86_expand_copysign (operands);
11064 (define_insn_and_split "copysign<mode>3_const"
11065 [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
11067 [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
11068 (match_operand:CSGNMODE 2 "register_operand" "0")
11069 (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
11071 "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
11072 || (TARGET_SSE2 && (<MODE>mode == TFmode))"
11074 "&& reload_completed"
11077 ix86_split_copysign_const (operands);
11081 (define_insn "copysign<mode>3_var"
11082 [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
11084 [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
11085 (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
11086 (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
11087 (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
11089 (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
11090 "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
11091 || (TARGET_SSE2 && (<MODE>mode == TFmode))"
11095 [(set (match_operand:CSGNMODE 0 "register_operand" "")
11097 [(match_operand:CSGNMODE 2 "register_operand" "")
11098 (match_operand:CSGNMODE 3 "register_operand" "")
11099 (match_operand:<CSGNVMODE> 4 "" "")
11100 (match_operand:<CSGNVMODE> 5 "" "")]
11102 (clobber (match_scratch:<CSGNVMODE> 1 ""))]
11103 "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
11104 || (TARGET_SSE2 && (<MODE>mode == TFmode)))
11105 && reload_completed"
11108 ix86_split_copysign_var (operands);
11112 ;; One complement instructions
11114 (define_expand "one_cmpldi2"
11115 [(set (match_operand:DI 0 "nonimmediate_operand" "")
11116 (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
11118 "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
11120 (define_insn "*one_cmpldi2_1_rex64"
11121 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11122 (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
11123 "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
11125 [(set_attr "type" "negnot")
11126 (set_attr "mode" "DI")])
11128 (define_insn "*one_cmpldi2_2_rex64"
11129 [(set (reg FLAGS_REG)
11130 (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
11132 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11133 (not:DI (match_dup 1)))]
11134 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
11135 && ix86_unary_operator_ok (NOT, DImode, operands)"
11137 [(set_attr "type" "alu1")
11138 (set_attr "mode" "DI")])
11141 [(set (match_operand 0 "flags_reg_operand" "")
11142 (match_operator 2 "compare_operator"
11143 [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
11145 (set (match_operand:DI 1 "nonimmediate_operand" "")
11146 (not:DI (match_dup 3)))]
11147 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
11148 [(parallel [(set (match_dup 0)
11150 [(xor:DI (match_dup 3) (const_int -1))
11153 (xor:DI (match_dup 3) (const_int -1)))])]
11156 (define_expand "one_cmplsi2"
11157 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11158 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
11160 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
11162 (define_insn "*one_cmplsi2_1"
11163 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11164 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
11165 "ix86_unary_operator_ok (NOT, SImode, operands)"
11167 [(set_attr "type" "negnot")
11168 (set_attr "mode" "SI")])
11170 ;; ??? Currently never generated - xor is used instead.
11171 (define_insn "*one_cmplsi2_1_zext"
11172 [(set (match_operand:DI 0 "register_operand" "=r")
11173 (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
11174 "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
11176 [(set_attr "type" "negnot")
11177 (set_attr "mode" "SI")])
11179 (define_insn "*one_cmplsi2_2"
11180 [(set (reg FLAGS_REG)
11181 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
11183 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11184 (not:SI (match_dup 1)))]
11185 "ix86_match_ccmode (insn, CCNOmode)
11186 && ix86_unary_operator_ok (NOT, SImode, operands)"
11188 [(set_attr "type" "alu1")
11189 (set_attr "mode" "SI")])
11192 [(set (match_operand 0 "flags_reg_operand" "")
11193 (match_operator 2 "compare_operator"
11194 [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
11196 (set (match_operand:SI 1 "nonimmediate_operand" "")
11197 (not:SI (match_dup 3)))]
11198 "ix86_match_ccmode (insn, CCNOmode)"
11199 [(parallel [(set (match_dup 0)
11200 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
11203 (xor:SI (match_dup 3) (const_int -1)))])]
11206 ;; ??? Currently never generated - xor is used instead.
11207 (define_insn "*one_cmplsi2_2_zext"
11208 [(set (reg FLAGS_REG)
11209 (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
11211 (set (match_operand:DI 0 "register_operand" "=r")
11212 (zero_extend:DI (not:SI (match_dup 1))))]
11213 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
11214 && ix86_unary_operator_ok (NOT, SImode, operands)"
11216 [(set_attr "type" "alu1")
11217 (set_attr "mode" "SI")])
11220 [(set (match_operand 0 "flags_reg_operand" "")
11221 (match_operator 2 "compare_operator"
11222 [(not:SI (match_operand:SI 3 "register_operand" ""))
11224 (set (match_operand:DI 1 "register_operand" "")
11225 (zero_extend:DI (not:SI (match_dup 3))))]
11226 "ix86_match_ccmode (insn, CCNOmode)"
11227 [(parallel [(set (match_dup 0)
11228 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
11231 (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
11234 (define_expand "one_cmplhi2"
11235 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11236 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
11237 "TARGET_HIMODE_MATH"
11238 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
11240 (define_insn "*one_cmplhi2_1"
11241 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11242 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
11243 "ix86_unary_operator_ok (NOT, HImode, operands)"
11245 [(set_attr "type" "negnot")
11246 (set_attr "mode" "HI")])
11248 (define_insn "*one_cmplhi2_2"
11249 [(set (reg FLAGS_REG)
11250 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
11252 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11253 (not:HI (match_dup 1)))]
11254 "ix86_match_ccmode (insn, CCNOmode)
11255 && ix86_unary_operator_ok (NEG, HImode, operands)"
11257 [(set_attr "type" "alu1")
11258 (set_attr "mode" "HI")])
11261 [(set (match_operand 0 "flags_reg_operand" "")
11262 (match_operator 2 "compare_operator"
11263 [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
11265 (set (match_operand:HI 1 "nonimmediate_operand" "")
11266 (not:HI (match_dup 3)))]
11267 "ix86_match_ccmode (insn, CCNOmode)"
11268 [(parallel [(set (match_dup 0)
11269 (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
11272 (xor:HI (match_dup 3) (const_int -1)))])]
11275 ;; %%% Potential partial reg stall on alternative 1. What to do?
11276 (define_expand "one_cmplqi2"
11277 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11278 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
11279 "TARGET_QIMODE_MATH"
11280 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
11282 (define_insn "*one_cmplqi2_1"
11283 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
11284 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
11285 "ix86_unary_operator_ok (NOT, QImode, operands)"
11289 [(set_attr "type" "negnot")
11290 (set_attr "mode" "QI,SI")])
11292 (define_insn "*one_cmplqi2_2"
11293 [(set (reg FLAGS_REG)
11294 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
11296 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11297 (not:QI (match_dup 1)))]
11298 "ix86_match_ccmode (insn, CCNOmode)
11299 && ix86_unary_operator_ok (NOT, QImode, operands)"
11301 [(set_attr "type" "alu1")
11302 (set_attr "mode" "QI")])
11305 [(set (match_operand 0 "flags_reg_operand" "")
11306 (match_operator 2 "compare_operator"
11307 [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
11309 (set (match_operand:QI 1 "nonimmediate_operand" "")
11310 (not:QI (match_dup 3)))]
11311 "ix86_match_ccmode (insn, CCNOmode)"
11312 [(parallel [(set (match_dup 0)
11313 (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
11316 (xor:QI (match_dup 3) (const_int -1)))])]
11319 ;; Arithmetic shift instructions
11321 ;; DImode shifts are implemented using the i386 "shift double" opcode,
11322 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count
11323 ;; is variable, then the count is in %cl and the "imm" operand is dropped
11324 ;; from the assembler input.
11326 ;; This instruction shifts the target reg/mem as usual, but instead of
11327 ;; shifting in zeros, bits are shifted in from reg operand. If the insn
11328 ;; is a left shift double, bits are taken from the high order bits of
11329 ;; reg, else if the insn is a shift right double, bits are taken from the
11330 ;; low order bits of reg. So if %eax is "1234" and %edx is "5678",
11331 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
11333 ;; Since sh[lr]d does not change the `reg' operand, that is done
11334 ;; separately, making all shifts emit pairs of shift double and normal
11335 ;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to
11336 ;; support a 63 bit shift, each shift where the count is in a reg expands
11337 ;; to a pair of shifts, a branch, a shift by 32 and a label.
11339 ;; If the shift count is a constant, we need never emit more than one
11340 ;; shift pair, instead using moves and sign extension for counts greater
11343 (define_expand "ashlti3"
11344 [(set (match_operand:TI 0 "register_operand" "")
11345 (ashift:TI (match_operand:TI 1 "reg_or_pm1_operand" "")
11346 (match_operand:QI 2 "nonmemory_operand" "")))]
11348 "ix86_expand_binary_operator (ASHIFT, TImode, operands); DONE;")
11350 ;; This pattern must be defined before *ashlti3_1 to prevent
11351 ;; combine pass from converting sse2_ashlti3 to *ashlti3_1.
11353 (define_insn "*avx_ashlti3"
11354 [(set (match_operand:TI 0 "register_operand" "=x")
11355 (ashift:TI (match_operand:TI 1 "register_operand" "x")
11356 (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
11359 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
11360 return "vpslldq\t{%2, %1, %0|%0, %1, %2}";
11362 [(set_attr "type" "sseishft")
11363 (set_attr "prefix" "vex")
11364 (set_attr "mode" "TI")])
11366 (define_insn "sse2_ashlti3"
11367 [(set (match_operand:TI 0 "register_operand" "=x")
11368 (ashift:TI (match_operand:TI 1 "register_operand" "0")
11369 (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
11372 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
11373 return "pslldq\t{%2, %0|%0, %2}";
11375 [(set_attr "type" "sseishft")
11376 (set_attr "prefix_data16" "1")
11377 (set_attr "mode" "TI")])
11379 (define_insn "*ashlti3_1"
11380 [(set (match_operand:TI 0 "register_operand" "=&r,r")
11381 (ashift:TI (match_operand:TI 1 "reg_or_pm1_operand" "n,0")
11382 (match_operand:QI 2 "nonmemory_operand" "Oc,Oc")))
11383 (clobber (reg:CC FLAGS_REG))]
11386 [(set_attr "type" "multi")])
11389 [(match_scratch:DI 3 "r")
11390 (parallel [(set (match_operand:TI 0 "register_operand" "")
11391 (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
11392 (match_operand:QI 2 "nonmemory_operand" "")))
11393 (clobber (reg:CC FLAGS_REG))])
11397 "ix86_split_ashl (operands, operands[3], TImode); DONE;")
11400 [(set (match_operand:TI 0 "register_operand" "")
11401 (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
11402 (match_operand:QI 2 "nonmemory_operand" "")))
11403 (clobber (reg:CC FLAGS_REG))]
11404 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11405 ? epilogue_completed : reload_completed)"
11407 "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;")
11409 (define_insn "x86_64_shld"
11410 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
11411 (ior:DI (ashift:DI (match_dup 0)
11412 (match_operand:QI 2 "nonmemory_operand" "Jc"))
11413 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
11414 (minus:QI (const_int 64) (match_dup 2)))))
11415 (clobber (reg:CC FLAGS_REG))]
11417 "shld{q}\t{%s2%1, %0|%0, %1, %2}"
11418 [(set_attr "type" "ishift")
11419 (set_attr "prefix_0f" "1")
11420 (set_attr "mode" "DI")
11421 (set_attr "athlon_decode" "vector")
11422 (set_attr "amdfam10_decode" "vector")])
11424 (define_expand "x86_64_shift_adj_1"
11425 [(set (reg:CCZ FLAGS_REG)
11426 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
11429 (set (match_operand:DI 0 "register_operand" "")
11430 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11431 (match_operand:DI 1 "register_operand" "")
11434 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11435 (match_operand:DI 3 "register_operand" "r")
11440 (define_expand "x86_64_shift_adj_2"
11441 [(use (match_operand:DI 0 "register_operand" ""))
11442 (use (match_operand:DI 1 "register_operand" ""))
11443 (use (match_operand:QI 2 "register_operand" ""))]
11446 rtx label = gen_label_rtx ();
11449 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (64)));
11451 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11452 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11453 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11454 gen_rtx_LABEL_REF (VOIDmode, label),
11456 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11457 JUMP_LABEL (tmp) = label;
11459 emit_move_insn (operands[0], operands[1]);
11460 ix86_expand_clear (operands[1]);
11462 emit_label (label);
11463 LABEL_NUSES (label) = 1;
11468 (define_expand "ashldi3"
11469 [(set (match_operand:DI 0 "shiftdi_operand" "")
11470 (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
11471 (match_operand:QI 2 "nonmemory_operand" "")))]
11473 "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
11475 (define_insn "*ashldi3_1_rex64"
11476 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
11477 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
11478 (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
11479 (clobber (reg:CC FLAGS_REG))]
11480 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11482 switch (get_attr_type (insn))
11485 gcc_assert (operands[2] == const1_rtx);
11486 gcc_assert (rtx_equal_p (operands[0], operands[1]));
11487 return "add{q}\t%0, %0";
11490 gcc_assert (CONST_INT_P (operands[2]));
11491 gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
11492 operands[1] = gen_rtx_MULT (DImode, operands[1],
11493 GEN_INT (1 << INTVAL (operands[2])));
11494 return "lea{q}\t{%a1, %0|%0, %a1}";
11497 if (REG_P (operands[2]))
11498 return "sal{q}\t{%b2, %0|%0, %b2}";
11499 else if (operands[2] == const1_rtx
11500 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11501 return "sal{q}\t%0";
11503 return "sal{q}\t{%2, %0|%0, %2}";
11506 [(set (attr "type")
11507 (cond [(eq_attr "alternative" "1")
11508 (const_string "lea")
11509 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11511 (match_operand 0 "register_operand" ""))
11512 (match_operand 2 "const1_operand" ""))
11513 (const_string "alu")
11515 (const_string "ishift")))
11516 (set_attr "mode" "DI")])
11518 ;; Convert lea to the lea pattern to avoid flags dependency.
11520 [(set (match_operand:DI 0 "register_operand" "")
11521 (ashift:DI (match_operand:DI 1 "index_register_operand" "")
11522 (match_operand:QI 2 "immediate_operand" "")))
11523 (clobber (reg:CC FLAGS_REG))]
11524 "TARGET_64BIT && reload_completed
11525 && true_regnum (operands[0]) != true_regnum (operands[1])"
11526 [(set (match_dup 0)
11527 (mult:DI (match_dup 1)
11529 "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
11531 ;; This pattern can't accept a variable shift count, since shifts by
11532 ;; zero don't affect the flags. We assume that shifts by constant
11533 ;; zero are optimized away.
11534 (define_insn "*ashldi3_cmp_rex64"
11535 [(set (reg FLAGS_REG)
11537 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11538 (match_operand:QI 2 "const_1_to_63_operand" "J"))
11540 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11541 (ashift:DI (match_dup 1) (match_dup 2)))]
11543 && (optimize_function_for_size_p (cfun)
11544 || !TARGET_PARTIAL_FLAG_REG_STALL
11545 || (operands[2] == const1_rtx
11547 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11548 && ix86_match_ccmode (insn, CCGOCmode)
11549 && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11551 switch (get_attr_type (insn))
11554 gcc_assert (operands[2] == const1_rtx);
11555 return "add{q}\t%0, %0";
11558 if (REG_P (operands[2]))
11559 return "sal{q}\t{%b2, %0|%0, %b2}";
11560 else if (operands[2] == const1_rtx
11561 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11562 return "sal{q}\t%0";
11564 return "sal{q}\t{%2, %0|%0, %2}";
11567 [(set (attr "type")
11568 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11570 (match_operand 0 "register_operand" ""))
11571 (match_operand 2 "const1_operand" ""))
11572 (const_string "alu")
11574 (const_string "ishift")))
11575 (set_attr "mode" "DI")])
11577 (define_insn "*ashldi3_cconly_rex64"
11578 [(set (reg FLAGS_REG)
11580 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11581 (match_operand:QI 2 "const_1_to_63_operand" "J"))
11583 (clobber (match_scratch:DI 0 "=r"))]
11585 && (optimize_function_for_size_p (cfun)
11586 || !TARGET_PARTIAL_FLAG_REG_STALL
11587 || (operands[2] == const1_rtx
11589 || TARGET_DOUBLE_WITH_ADD)))
11590 && ix86_match_ccmode (insn, CCGOCmode)
11591 && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11593 switch (get_attr_type (insn))
11596 gcc_assert (operands[2] == const1_rtx);
11597 return "add{q}\t%0, %0";
11600 if (REG_P (operands[2]))
11601 return "sal{q}\t{%b2, %0|%0, %b2}";
11602 else if (operands[2] == const1_rtx
11603 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11604 return "sal{q}\t%0";
11606 return "sal{q}\t{%2, %0|%0, %2}";
11609 [(set (attr "type")
11610 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11612 (match_operand 0 "register_operand" ""))
11613 (match_operand 2 "const1_operand" ""))
11614 (const_string "alu")
11616 (const_string "ishift")))
11617 (set_attr "mode" "DI")])
11619 (define_insn "*ashldi3_1"
11620 [(set (match_operand:DI 0 "register_operand" "=&r,r")
11621 (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
11622 (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
11623 (clobber (reg:CC FLAGS_REG))]
11626 [(set_attr "type" "multi")])
11628 ;; By default we don't ask for a scratch register, because when DImode
11629 ;; values are manipulated, registers are already at a premium. But if
11630 ;; we have one handy, we won't turn it away.
11632 [(match_scratch:SI 3 "r")
11633 (parallel [(set (match_operand:DI 0 "register_operand" "")
11634 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11635 (match_operand:QI 2 "nonmemory_operand" "")))
11636 (clobber (reg:CC FLAGS_REG))])
11638 "!TARGET_64BIT && TARGET_CMOVE"
11640 "ix86_split_ashl (operands, operands[3], DImode); DONE;")
11643 [(set (match_operand:DI 0 "register_operand" "")
11644 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11645 (match_operand:QI 2 "nonmemory_operand" "")))
11646 (clobber (reg:CC FLAGS_REG))]
11647 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11648 ? epilogue_completed : reload_completed)"
11650 "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;")
11652 (define_insn "x86_shld"
11653 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
11654 (ior:SI (ashift:SI (match_dup 0)
11655 (match_operand:QI 2 "nonmemory_operand" "Ic"))
11656 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
11657 (minus:QI (const_int 32) (match_dup 2)))))
11658 (clobber (reg:CC FLAGS_REG))]
11660 "shld{l}\t{%s2%1, %0|%0, %1, %2}"
11661 [(set_attr "type" "ishift")
11662 (set_attr "prefix_0f" "1")
11663 (set_attr "mode" "SI")
11664 (set_attr "pent_pair" "np")
11665 (set_attr "athlon_decode" "vector")
11666 (set_attr "amdfam10_decode" "vector")])
11668 (define_expand "x86_shift_adj_1"
11669 [(set (reg:CCZ FLAGS_REG)
11670 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
11673 (set (match_operand:SI 0 "register_operand" "")
11674 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11675 (match_operand:SI 1 "register_operand" "")
11678 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11679 (match_operand:SI 3 "register_operand" "r")
11684 (define_expand "x86_shift_adj_2"
11685 [(use (match_operand:SI 0 "register_operand" ""))
11686 (use (match_operand:SI 1 "register_operand" ""))
11687 (use (match_operand:QI 2 "register_operand" ""))]
11690 rtx label = gen_label_rtx ();
11693 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11695 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11696 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11697 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11698 gen_rtx_LABEL_REF (VOIDmode, label),
11700 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11701 JUMP_LABEL (tmp) = label;
11703 emit_move_insn (operands[0], operands[1]);
11704 ix86_expand_clear (operands[1]);
11706 emit_label (label);
11707 LABEL_NUSES (label) = 1;
11712 (define_expand "ashlsi3"
11713 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11714 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
11715 (match_operand:QI 2 "nonmemory_operand" "")))]
11717 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
11719 (define_insn "*ashlsi3_1"
11720 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
11721 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
11722 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11723 (clobber (reg:CC FLAGS_REG))]
11724 "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11726 switch (get_attr_type (insn))
11729 gcc_assert (operands[2] == const1_rtx);
11730 gcc_assert (rtx_equal_p (operands[0], operands[1]));
11731 return "add{l}\t%0, %0";
11737 if (REG_P (operands[2]))
11738 return "sal{l}\t{%b2, %0|%0, %b2}";
11739 else if (operands[2] == const1_rtx
11740 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11741 return "sal{l}\t%0";
11743 return "sal{l}\t{%2, %0|%0, %2}";
11746 [(set (attr "type")
11747 (cond [(eq_attr "alternative" "1")
11748 (const_string "lea")
11749 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11751 (match_operand 0 "register_operand" ""))
11752 (match_operand 2 "const1_operand" ""))
11753 (const_string "alu")
11755 (const_string "ishift")))
11756 (set_attr "mode" "SI")])
11758 ;; Convert lea to the lea pattern to avoid flags dependency.
11760 [(set (match_operand 0 "register_operand" "")
11761 (ashift (match_operand 1 "index_register_operand" "")
11762 (match_operand:QI 2 "const_int_operand" "")))
11763 (clobber (reg:CC FLAGS_REG))]
11765 && true_regnum (operands[0]) != true_regnum (operands[1])
11766 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
11770 enum machine_mode mode = GET_MODE (operands[0]);
11772 if (GET_MODE_SIZE (mode) < 4)
11773 operands[0] = gen_lowpart (SImode, operands[0]);
11775 operands[1] = gen_lowpart (Pmode, operands[1]);
11776 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11778 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
11779 if (Pmode != SImode)
11780 pat = gen_rtx_SUBREG (SImode, pat, 0);
11781 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
11785 ;; Rare case of shifting RSP is handled by generating move and shift
11787 [(set (match_operand 0 "register_operand" "")
11788 (ashift (match_operand 1 "register_operand" "")
11789 (match_operand:QI 2 "const_int_operand" "")))
11790 (clobber (reg:CC FLAGS_REG))]
11792 && true_regnum (operands[0]) != true_regnum (operands[1])"
11796 emit_move_insn (operands[0], operands[1]);
11797 pat = gen_rtx_SET (VOIDmode, operands[0],
11798 gen_rtx_ASHIFT (GET_MODE (operands[0]),
11799 operands[0], operands[2]));
11800 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
11801 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
11805 (define_insn "*ashlsi3_1_zext"
11806 [(set (match_operand:DI 0 "register_operand" "=r,r")
11807 (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
11808 (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
11809 (clobber (reg:CC FLAGS_REG))]
11810 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11812 switch (get_attr_type (insn))
11815 gcc_assert (operands[2] == const1_rtx);
11816 return "add{l}\t%k0, %k0";
11822 if (REG_P (operands[2]))
11823 return "sal{l}\t{%b2, %k0|%k0, %b2}";
11824 else if (operands[2] == const1_rtx
11825 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11826 return "sal{l}\t%k0";
11828 return "sal{l}\t{%2, %k0|%k0, %2}";
11831 [(set (attr "type")
11832 (cond [(eq_attr "alternative" "1")
11833 (const_string "lea")
11834 (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11836 (match_operand 2 "const1_operand" ""))
11837 (const_string "alu")
11839 (const_string "ishift")))
11840 (set_attr "mode" "SI")])
11842 ;; Convert lea to the lea pattern to avoid flags dependency.
11844 [(set (match_operand:DI 0 "register_operand" "")
11845 (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
11846 (match_operand:QI 2 "const_int_operand" ""))))
11847 (clobber (reg:CC FLAGS_REG))]
11848 "TARGET_64BIT && reload_completed
11849 && true_regnum (operands[0]) != true_regnum (operands[1])"
11850 [(set (match_dup 0) (zero_extend:DI
11851 (subreg:SI (mult:SI (match_dup 1)
11852 (match_dup 2)) 0)))]
11854 operands[1] = gen_lowpart (Pmode, operands[1]);
11855 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11858 ;; This pattern can't accept a variable shift count, since shifts by
11859 ;; zero don't affect the flags. We assume that shifts by constant
11860 ;; zero are optimized away.
11861 (define_insn "*ashlsi3_cmp"
11862 [(set (reg FLAGS_REG)
11864 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11865 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11867 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11868 (ashift:SI (match_dup 1) (match_dup 2)))]
11869 "(optimize_function_for_size_p (cfun)
11870 || !TARGET_PARTIAL_FLAG_REG_STALL
11871 || (operands[2] == const1_rtx
11873 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11874 && ix86_match_ccmode (insn, CCGOCmode)
11875 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11877 switch (get_attr_type (insn))
11880 gcc_assert (operands[2] == const1_rtx);
11881 return "add{l}\t%0, %0";
11884 if (REG_P (operands[2]))
11885 return "sal{l}\t{%b2, %0|%0, %b2}";
11886 else if (operands[2] == const1_rtx
11887 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11888 return "sal{l}\t%0";
11890 return "sal{l}\t{%2, %0|%0, %2}";
11893 [(set (attr "type")
11894 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11896 (match_operand 0 "register_operand" ""))
11897 (match_operand 2 "const1_operand" ""))
11898 (const_string "alu")
11900 (const_string "ishift")))
11901 (set_attr "mode" "SI")])
11903 (define_insn "*ashlsi3_cconly"
11904 [(set (reg FLAGS_REG)
11906 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11907 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11909 (clobber (match_scratch:SI 0 "=r"))]
11910 "(optimize_function_for_size_p (cfun)
11911 || !TARGET_PARTIAL_FLAG_REG_STALL
11912 || (operands[2] == const1_rtx
11914 || TARGET_DOUBLE_WITH_ADD)))
11915 && ix86_match_ccmode (insn, CCGOCmode)
11916 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11918 switch (get_attr_type (insn))
11921 gcc_assert (operands[2] == const1_rtx);
11922 return "add{l}\t%0, %0";
11925 if (REG_P (operands[2]))
11926 return "sal{l}\t{%b2, %0|%0, %b2}";
11927 else if (operands[2] == const1_rtx
11928 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11929 return "sal{l}\t%0";
11931 return "sal{l}\t{%2, %0|%0, %2}";
11934 [(set (attr "type")
11935 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11937 (match_operand 0 "register_operand" ""))
11938 (match_operand 2 "const1_operand" ""))
11939 (const_string "alu")
11941 (const_string "ishift")))
11942 (set_attr "mode" "SI")])
11944 (define_insn "*ashlsi3_cmp_zext"
11945 [(set (reg FLAGS_REG)
11947 (ashift:SI (match_operand:SI 1 "register_operand" "0")
11948 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11950 (set (match_operand:DI 0 "register_operand" "=r")
11951 (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
11953 && (optimize_function_for_size_p (cfun)
11954 || !TARGET_PARTIAL_FLAG_REG_STALL
11955 || (operands[2] == const1_rtx
11957 || TARGET_DOUBLE_WITH_ADD)))
11958 && ix86_match_ccmode (insn, CCGOCmode)
11959 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11961 switch (get_attr_type (insn))
11964 gcc_assert (operands[2] == const1_rtx);
11965 return "add{l}\t%k0, %k0";
11968 if (REG_P (operands[2]))
11969 return "sal{l}\t{%b2, %k0|%k0, %b2}";
11970 else if (operands[2] == const1_rtx
11971 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
11972 return "sal{l}\t%k0";
11974 return "sal{l}\t{%2, %k0|%k0, %2}";
11977 [(set (attr "type")
11978 (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11980 (match_operand 2 "const1_operand" ""))
11981 (const_string "alu")
11983 (const_string "ishift")))
11984 (set_attr "mode" "SI")])
11986 (define_expand "ashlhi3"
11987 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11988 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
11989 (match_operand:QI 2 "nonmemory_operand" "")))]
11990 "TARGET_HIMODE_MATH"
11991 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
11993 (define_insn "*ashlhi3_1_lea"
11994 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
11995 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
11996 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11997 (clobber (reg:CC FLAGS_REG))]
11998 "!TARGET_PARTIAL_REG_STALL
11999 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
12001 switch (get_attr_type (insn))
12006 gcc_assert (operands[2] == const1_rtx);
12007 return "add{w}\t%0, %0";
12010 if (REG_P (operands[2]))
12011 return "sal{w}\t{%b2, %0|%0, %b2}";
12012 else if (operands[2] == const1_rtx
12013 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12014 return "sal{w}\t%0";
12016 return "sal{w}\t{%2, %0|%0, %2}";
12019 [(set (attr "type")
12020 (cond [(eq_attr "alternative" "1")
12021 (const_string "lea")
12022 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12024 (match_operand 0 "register_operand" ""))
12025 (match_operand 2 "const1_operand" ""))
12026 (const_string "alu")
12028 (const_string "ishift")))
12029 (set_attr "mode" "HI,SI")])
12031 (define_insn "*ashlhi3_1"
12032 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12033 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12034 (match_operand:QI 2 "nonmemory_operand" "cI")))
12035 (clobber (reg:CC FLAGS_REG))]
12036 "TARGET_PARTIAL_REG_STALL
12037 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
12039 switch (get_attr_type (insn))
12042 gcc_assert (operands[2] == const1_rtx);
12043 return "add{w}\t%0, %0";
12046 if (REG_P (operands[2]))
12047 return "sal{w}\t{%b2, %0|%0, %b2}";
12048 else if (operands[2] == const1_rtx
12049 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12050 return "sal{w}\t%0";
12052 return "sal{w}\t{%2, %0|%0, %2}";
12055 [(set (attr "type")
12056 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12058 (match_operand 0 "register_operand" ""))
12059 (match_operand 2 "const1_operand" ""))
12060 (const_string "alu")
12062 (const_string "ishift")))
12063 (set_attr "mode" "HI")])
12065 ;; This pattern can't accept a variable shift count, since shifts by
12066 ;; zero don't affect the flags. We assume that shifts by constant
12067 ;; zero are optimized away.
12068 (define_insn "*ashlhi3_cmp"
12069 [(set (reg FLAGS_REG)
12071 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12072 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12074 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12075 (ashift:HI (match_dup 1) (match_dup 2)))]
12076 "(optimize_function_for_size_p (cfun)
12077 || !TARGET_PARTIAL_FLAG_REG_STALL
12078 || (operands[2] == const1_rtx
12080 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
12081 && ix86_match_ccmode (insn, CCGOCmode)
12082 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
12084 switch (get_attr_type (insn))
12087 gcc_assert (operands[2] == const1_rtx);
12088 return "add{w}\t%0, %0";
12091 if (REG_P (operands[2]))
12092 return "sal{w}\t{%b2, %0|%0, %b2}";
12093 else if (operands[2] == const1_rtx
12094 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12095 return "sal{w}\t%0";
12097 return "sal{w}\t{%2, %0|%0, %2}";
12100 [(set (attr "type")
12101 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12103 (match_operand 0 "register_operand" ""))
12104 (match_operand 2 "const1_operand" ""))
12105 (const_string "alu")
12107 (const_string "ishift")))
12108 (set_attr "mode" "HI")])
12110 (define_insn "*ashlhi3_cconly"
12111 [(set (reg FLAGS_REG)
12113 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12114 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12116 (clobber (match_scratch:HI 0 "=r"))]
12117 "(optimize_function_for_size_p (cfun)
12118 || !TARGET_PARTIAL_FLAG_REG_STALL
12119 || (operands[2] == const1_rtx
12121 || TARGET_DOUBLE_WITH_ADD)))
12122 && ix86_match_ccmode (insn, CCGOCmode)
12123 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
12125 switch (get_attr_type (insn))
12128 gcc_assert (operands[2] == const1_rtx);
12129 return "add{w}\t%0, %0";
12132 if (REG_P (operands[2]))
12133 return "sal{w}\t{%b2, %0|%0, %b2}";
12134 else if (operands[2] == const1_rtx
12135 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12136 return "sal{w}\t%0";
12138 return "sal{w}\t{%2, %0|%0, %2}";
12141 [(set (attr "type")
12142 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12144 (match_operand 0 "register_operand" ""))
12145 (match_operand 2 "const1_operand" ""))
12146 (const_string "alu")
12148 (const_string "ishift")))
12149 (set_attr "mode" "HI")])
12151 (define_expand "ashlqi3"
12152 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12153 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
12154 (match_operand:QI 2 "nonmemory_operand" "")))]
12155 "TARGET_QIMODE_MATH"
12156 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
12158 ;; %%% Potential partial reg stall on alternative 2. What to do?
12160 (define_insn "*ashlqi3_1_lea"
12161 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
12162 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
12163 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
12164 (clobber (reg:CC FLAGS_REG))]
12165 "!TARGET_PARTIAL_REG_STALL
12166 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
12168 switch (get_attr_type (insn))
12173 gcc_assert (operands[2] == const1_rtx);
12174 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
12175 return "add{l}\t%k0, %k0";
12177 return "add{b}\t%0, %0";
12180 if (REG_P (operands[2]))
12182 if (get_attr_mode (insn) == MODE_SI)
12183 return "sal{l}\t{%b2, %k0|%k0, %b2}";
12185 return "sal{b}\t{%b2, %0|%0, %b2}";
12187 else if (operands[2] == const1_rtx
12188 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12190 if (get_attr_mode (insn) == MODE_SI)
12191 return "sal{l}\t%0";
12193 return "sal{b}\t%0";
12197 if (get_attr_mode (insn) == MODE_SI)
12198 return "sal{l}\t{%2, %k0|%k0, %2}";
12200 return "sal{b}\t{%2, %0|%0, %2}";
12204 [(set (attr "type")
12205 (cond [(eq_attr "alternative" "2")
12206 (const_string "lea")
12207 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12209 (match_operand 0 "register_operand" ""))
12210 (match_operand 2 "const1_operand" ""))
12211 (const_string "alu")
12213 (const_string "ishift")))
12214 (set_attr "mode" "QI,SI,SI")])
12216 (define_insn "*ashlqi3_1"
12217 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
12218 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12219 (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
12220 (clobber (reg:CC FLAGS_REG))]
12221 "TARGET_PARTIAL_REG_STALL
12222 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
12224 switch (get_attr_type (insn))
12227 gcc_assert (operands[2] == const1_rtx);
12228 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
12229 return "add{l}\t%k0, %k0";
12231 return "add{b}\t%0, %0";
12234 if (REG_P (operands[2]))
12236 if (get_attr_mode (insn) == MODE_SI)
12237 return "sal{l}\t{%b2, %k0|%k0, %b2}";
12239 return "sal{b}\t{%b2, %0|%0, %b2}";
12241 else if (operands[2] == const1_rtx
12242 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12244 if (get_attr_mode (insn) == MODE_SI)
12245 return "sal{l}\t%0";
12247 return "sal{b}\t%0";
12251 if (get_attr_mode (insn) == MODE_SI)
12252 return "sal{l}\t{%2, %k0|%k0, %2}";
12254 return "sal{b}\t{%2, %0|%0, %2}";
12258 [(set (attr "type")
12259 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12261 (match_operand 0 "register_operand" ""))
12262 (match_operand 2 "const1_operand" ""))
12263 (const_string "alu")
12265 (const_string "ishift")))
12266 (set_attr "mode" "QI,SI")])
12268 ;; This pattern can't accept a variable shift count, since shifts by
12269 ;; zero don't affect the flags. We assume that shifts by constant
12270 ;; zero are optimized away.
12271 (define_insn "*ashlqi3_cmp"
12272 [(set (reg FLAGS_REG)
12274 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12275 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12277 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12278 (ashift:QI (match_dup 1) (match_dup 2)))]
12279 "(optimize_function_for_size_p (cfun)
12280 || !TARGET_PARTIAL_FLAG_REG_STALL
12281 || (operands[2] == const1_rtx
12283 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
12284 && ix86_match_ccmode (insn, CCGOCmode)
12285 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
12287 switch (get_attr_type (insn))
12290 gcc_assert (operands[2] == const1_rtx);
12291 return "add{b}\t%0, %0";
12294 if (REG_P (operands[2]))
12295 return "sal{b}\t{%b2, %0|%0, %b2}";
12296 else if (operands[2] == const1_rtx
12297 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12298 return "sal{b}\t%0";
12300 return "sal{b}\t{%2, %0|%0, %2}";
12303 [(set (attr "type")
12304 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12306 (match_operand 0 "register_operand" ""))
12307 (match_operand 2 "const1_operand" ""))
12308 (const_string "alu")
12310 (const_string "ishift")))
12311 (set_attr "mode" "QI")])
12313 (define_insn "*ashlqi3_cconly"
12314 [(set (reg FLAGS_REG)
12316 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12317 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12319 (clobber (match_scratch:QI 0 "=q"))]
12320 "(optimize_function_for_size_p (cfun)
12321 || !TARGET_PARTIAL_FLAG_REG_STALL
12322 || (operands[2] == const1_rtx
12324 || TARGET_DOUBLE_WITH_ADD)))
12325 && ix86_match_ccmode (insn, CCGOCmode)
12326 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
12328 switch (get_attr_type (insn))
12331 gcc_assert (operands[2] == const1_rtx);
12332 return "add{b}\t%0, %0";
12335 if (REG_P (operands[2]))
12336 return "sal{b}\t{%b2, %0|%0, %b2}";
12337 else if (operands[2] == const1_rtx
12338 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
12339 return "sal{b}\t%0";
12341 return "sal{b}\t{%2, %0|%0, %2}";
12344 [(set (attr "type")
12345 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
12347 (match_operand 0 "register_operand" ""))
12348 (match_operand 2 "const1_operand" ""))
12349 (const_string "alu")
12351 (const_string "ishift")))
12352 (set_attr "mode" "QI")])
12354 ;; See comment above `ashldi3' about how this works.
12356 (define_expand "ashrti3"
12357 [(set (match_operand:TI 0 "register_operand" "")
12358 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
12359 (match_operand:QI 2 "nonmemory_operand" "")))]
12361 "ix86_expand_binary_operator (ASHIFTRT, TImode, operands); DONE;")
12363 (define_insn "*ashrti3_1"
12364 [(set (match_operand:TI 0 "register_operand" "=r")
12365 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
12366 (match_operand:QI 2 "nonmemory_operand" "Oc")))
12367 (clobber (reg:CC FLAGS_REG))]
12370 [(set_attr "type" "multi")])
12373 [(match_scratch:DI 3 "r")
12374 (parallel [(set (match_operand:TI 0 "register_operand" "")
12375 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
12376 (match_operand:QI 2 "nonmemory_operand" "")))
12377 (clobber (reg:CC FLAGS_REG))])
12381 "ix86_split_ashr (operands, operands[3], TImode); DONE;")
12384 [(set (match_operand:TI 0 "register_operand" "")
12385 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
12386 (match_operand:QI 2 "nonmemory_operand" "")))
12387 (clobber (reg:CC FLAGS_REG))]
12388 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12389 ? epilogue_completed : reload_completed)"
12391 "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;")
12393 (define_insn "x86_64_shrd"
12394 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
12395 (ior:DI (ashiftrt:DI (match_dup 0)
12396 (match_operand:QI 2 "nonmemory_operand" "Jc"))
12397 (ashift:DI (match_operand:DI 1 "register_operand" "r")
12398 (minus:QI (const_int 64) (match_dup 2)))))
12399 (clobber (reg:CC FLAGS_REG))]
12401 "shrd{q}\t{%s2%1, %0|%0, %1, %2}"
12402 [(set_attr "type" "ishift")
12403 (set_attr "prefix_0f" "1")
12404 (set_attr "mode" "DI")
12405 (set_attr "athlon_decode" "vector")
12406 (set_attr "amdfam10_decode" "vector")])
12408 (define_expand "ashrdi3"
12409 [(set (match_operand:DI 0 "shiftdi_operand" "")
12410 (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
12411 (match_operand:QI 2 "nonmemory_operand" "")))]
12413 "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
12415 (define_expand "x86_64_shift_adj_3"
12416 [(use (match_operand:DI 0 "register_operand" ""))
12417 (use (match_operand:DI 1 "register_operand" ""))
12418 (use (match_operand:QI 2 "register_operand" ""))]
12421 rtx label = gen_label_rtx ();
12424 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (64)));
12426 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
12427 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
12428 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
12429 gen_rtx_LABEL_REF (VOIDmode, label),
12431 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
12432 JUMP_LABEL (tmp) = label;
12434 emit_move_insn (operands[0], operands[1]);
12435 emit_insn (gen_ashrdi3_63_rex64 (operands[1], operands[1], GEN_INT (63)));
12437 emit_label (label);
12438 LABEL_NUSES (label) = 1;
12443 (define_insn "ashrdi3_63_rex64"
12444 [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
12445 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
12446 (match_operand:DI 2 "const_int_operand" "i,i")))
12447 (clobber (reg:CC FLAGS_REG))]
12448 "TARGET_64BIT && INTVAL (operands[2]) == 63
12449 && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
12450 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12453 sar{q}\t{%2, %0|%0, %2}"
12454 [(set_attr "type" "imovx,ishift")
12455 (set_attr "prefix_0f" "0,*")
12456 (set_attr "length_immediate" "0,*")
12457 (set_attr "modrm" "0,1")
12458 (set_attr "mode" "DI")])
12460 (define_insn "*ashrdi3_1_one_bit_rex64"
12461 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12462 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12463 (match_operand:QI 2 "const1_operand" "")))
12464 (clobber (reg:CC FLAGS_REG))]
12466 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12467 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12469 [(set_attr "type" "ishift")
12470 (set (attr "length")
12471 (if_then_else (match_operand:DI 0 "register_operand" "")
12473 (const_string "*")))])
12475 (define_insn "*ashrdi3_1_rex64"
12476 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12477 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12478 (match_operand:QI 2 "nonmemory_operand" "J,c")))
12479 (clobber (reg:CC FLAGS_REG))]
12480 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12482 sar{q}\t{%2, %0|%0, %2}
12483 sar{q}\t{%b2, %0|%0, %b2}"
12484 [(set_attr "type" "ishift")
12485 (set_attr "mode" "DI")])
12487 ;; This pattern can't accept a variable shift count, since shifts by
12488 ;; zero don't affect the flags. We assume that shifts by constant
12489 ;; zero are optimized away.
12490 (define_insn "*ashrdi3_one_bit_cmp_rex64"
12491 [(set (reg FLAGS_REG)
12493 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12494 (match_operand:QI 2 "const1_operand" ""))
12496 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12497 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
12499 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12500 && ix86_match_ccmode (insn, CCGOCmode)
12501 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12503 [(set_attr "type" "ishift")
12504 (set (attr "length")
12505 (if_then_else (match_operand:DI 0 "register_operand" "")
12507 (const_string "*")))])
12509 (define_insn "*ashrdi3_one_bit_cconly_rex64"
12510 [(set (reg FLAGS_REG)
12512 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12513 (match_operand:QI 2 "const1_operand" ""))
12515 (clobber (match_scratch:DI 0 "=r"))]
12517 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12518 && ix86_match_ccmode (insn, CCGOCmode)
12519 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12521 [(set_attr "type" "ishift")
12522 (set_attr "length" "2")])
12524 ;; This pattern can't accept a variable shift count, since shifts by
12525 ;; zero don't affect the flags. We assume that shifts by constant
12526 ;; zero are optimized away.
12527 (define_insn "*ashrdi3_cmp_rex64"
12528 [(set (reg FLAGS_REG)
12530 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12531 (match_operand:QI 2 "const_1_to_63_operand" "J"))
12533 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12534 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
12536 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12537 && ix86_match_ccmode (insn, CCGOCmode)
12538 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12539 "sar{q}\t{%2, %0|%0, %2}"
12540 [(set_attr "type" "ishift")
12541 (set_attr "mode" "DI")])
12543 (define_insn "*ashrdi3_cconly_rex64"
12544 [(set (reg FLAGS_REG)
12546 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12547 (match_operand:QI 2 "const_1_to_63_operand" "J"))
12549 (clobber (match_scratch:DI 0 "=r"))]
12551 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12552 && ix86_match_ccmode (insn, CCGOCmode)
12553 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12554 "sar{q}\t{%2, %0|%0, %2}"
12555 [(set_attr "type" "ishift")
12556 (set_attr "mode" "DI")])
12558 (define_insn "*ashrdi3_1"
12559 [(set (match_operand:DI 0 "register_operand" "=r")
12560 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
12561 (match_operand:QI 2 "nonmemory_operand" "Jc")))
12562 (clobber (reg:CC FLAGS_REG))]
12565 [(set_attr "type" "multi")])
12567 ;; By default we don't ask for a scratch register, because when DImode
12568 ;; values are manipulated, registers are already at a premium. But if
12569 ;; we have one handy, we won't turn it away.
12571 [(match_scratch:SI 3 "r")
12572 (parallel [(set (match_operand:DI 0 "register_operand" "")
12573 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
12574 (match_operand:QI 2 "nonmemory_operand" "")))
12575 (clobber (reg:CC FLAGS_REG))])
12577 "!TARGET_64BIT && TARGET_CMOVE"
12579 "ix86_split_ashr (operands, operands[3], DImode); DONE;")
12582 [(set (match_operand:DI 0 "register_operand" "")
12583 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
12584 (match_operand:QI 2 "nonmemory_operand" "")))
12585 (clobber (reg:CC FLAGS_REG))]
12586 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12587 ? epilogue_completed : reload_completed)"
12589 "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;")
12591 (define_insn "x86_shrd"
12592 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
12593 (ior:SI (ashiftrt:SI (match_dup 0)
12594 (match_operand:QI 2 "nonmemory_operand" "Ic"))
12595 (ashift:SI (match_operand:SI 1 "register_operand" "r")
12596 (minus:QI (const_int 32) (match_dup 2)))))
12597 (clobber (reg:CC FLAGS_REG))]
12599 "shrd{l}\t{%s2%1, %0|%0, %1, %2}"
12600 [(set_attr "type" "ishift")
12601 (set_attr "prefix_0f" "1")
12602 (set_attr "pent_pair" "np")
12603 (set_attr "mode" "SI")])
12605 (define_expand "x86_shift_adj_3"
12606 [(use (match_operand:SI 0 "register_operand" ""))
12607 (use (match_operand:SI 1 "register_operand" ""))
12608 (use (match_operand:QI 2 "register_operand" ""))]
12611 rtx label = gen_label_rtx ();
12614 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
12616 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
12617 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
12618 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
12619 gen_rtx_LABEL_REF (VOIDmode, label),
12621 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
12622 JUMP_LABEL (tmp) = label;
12624 emit_move_insn (operands[0], operands[1]);
12625 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
12627 emit_label (label);
12628 LABEL_NUSES (label) = 1;
12633 (define_expand "ashrsi3_31"
12634 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
12635 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
12636 (match_operand:SI 2 "const_int_operand" "i,i")))
12637 (clobber (reg:CC FLAGS_REG))])]
12640 (define_insn "*ashrsi3_31"
12641 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
12642 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
12643 (match_operand:SI 2 "const_int_operand" "i,i")))
12644 (clobber (reg:CC FLAGS_REG))]
12645 "INTVAL (operands[2]) == 31
12646 && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
12647 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12650 sar{l}\t{%2, %0|%0, %2}"
12651 [(set_attr "type" "imovx,ishift")
12652 (set_attr "prefix_0f" "0,*")
12653 (set_attr "length_immediate" "0,*")
12654 (set_attr "modrm" "0,1")
12655 (set_attr "mode" "SI")])
12657 (define_insn "*ashrsi3_31_zext"
12658 [(set (match_operand:DI 0 "register_operand" "=*d,r")
12659 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
12660 (match_operand:SI 2 "const_int_operand" "i,i"))))
12661 (clobber (reg:CC FLAGS_REG))]
12662 "TARGET_64BIT && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
12663 && INTVAL (operands[2]) == 31
12664 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12667 sar{l}\t{%2, %k0|%k0, %2}"
12668 [(set_attr "type" "imovx,ishift")
12669 (set_attr "prefix_0f" "0,*")
12670 (set_attr "length_immediate" "0,*")
12671 (set_attr "modrm" "0,1")
12672 (set_attr "mode" "SI")])
12674 (define_expand "ashrsi3"
12675 [(set (match_operand:SI 0 "nonimmediate_operand" "")
12676 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12677 (match_operand:QI 2 "nonmemory_operand" "")))]
12679 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
12681 (define_insn "*ashrsi3_1_one_bit"
12682 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12683 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12684 (match_operand:QI 2 "const1_operand" "")))
12685 (clobber (reg:CC FLAGS_REG))]
12686 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12687 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12689 [(set_attr "type" "ishift")
12690 (set (attr "length")
12691 (if_then_else (match_operand:SI 0 "register_operand" "")
12693 (const_string "*")))])
12695 (define_insn "*ashrsi3_1_one_bit_zext"
12696 [(set (match_operand:DI 0 "register_operand" "=r")
12697 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12698 (match_operand:QI 2 "const1_operand" ""))))
12699 (clobber (reg:CC FLAGS_REG))]
12701 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12702 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12704 [(set_attr "type" "ishift")
12705 (set_attr "length" "2")])
12707 (define_insn "*ashrsi3_1"
12708 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12709 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12710 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12711 (clobber (reg:CC FLAGS_REG))]
12712 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12714 sar{l}\t{%2, %0|%0, %2}
12715 sar{l}\t{%b2, %0|%0, %b2}"
12716 [(set_attr "type" "ishift")
12717 (set_attr "mode" "SI")])
12719 (define_insn "*ashrsi3_1_zext"
12720 [(set (match_operand:DI 0 "register_operand" "=r,r")
12721 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
12722 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12723 (clobber (reg:CC FLAGS_REG))]
12724 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12726 sar{l}\t{%2, %k0|%k0, %2}
12727 sar{l}\t{%b2, %k0|%k0, %b2}"
12728 [(set_attr "type" "ishift")
12729 (set_attr "mode" "SI")])
12731 ;; This pattern can't accept a variable shift count, since shifts by
12732 ;; zero don't affect the flags. We assume that shifts by constant
12733 ;; zero are optimized away.
12734 (define_insn "*ashrsi3_one_bit_cmp"
12735 [(set (reg FLAGS_REG)
12737 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12738 (match_operand:QI 2 "const1_operand" ""))
12740 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12741 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12742 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12743 && ix86_match_ccmode (insn, CCGOCmode)
12744 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12746 [(set_attr "type" "ishift")
12747 (set (attr "length")
12748 (if_then_else (match_operand:SI 0 "register_operand" "")
12750 (const_string "*")))])
12752 (define_insn "*ashrsi3_one_bit_cconly"
12753 [(set (reg FLAGS_REG)
12755 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12756 (match_operand:QI 2 "const1_operand" ""))
12758 (clobber (match_scratch:SI 0 "=r"))]
12759 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12760 && ix86_match_ccmode (insn, CCGOCmode)
12761 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12763 [(set_attr "type" "ishift")
12764 (set_attr "length" "2")])
12766 (define_insn "*ashrsi3_one_bit_cmp_zext"
12767 [(set (reg FLAGS_REG)
12769 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12770 (match_operand:QI 2 "const1_operand" ""))
12772 (set (match_operand:DI 0 "register_operand" "=r")
12773 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12775 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12776 && ix86_match_ccmode (insn, CCmode)
12777 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12779 [(set_attr "type" "ishift")
12780 (set_attr "length" "2")])
12782 ;; This pattern can't accept a variable shift count, since shifts by
12783 ;; zero don't affect the flags. We assume that shifts by constant
12784 ;; zero are optimized away.
12785 (define_insn "*ashrsi3_cmp"
12786 [(set (reg FLAGS_REG)
12788 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12789 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12791 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12792 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12793 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12794 && ix86_match_ccmode (insn, CCGOCmode)
12795 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12796 "sar{l}\t{%2, %0|%0, %2}"
12797 [(set_attr "type" "ishift")
12798 (set_attr "mode" "SI")])
12800 (define_insn "*ashrsi3_cconly"
12801 [(set (reg FLAGS_REG)
12803 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12804 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12806 (clobber (match_scratch:SI 0 "=r"))]
12807 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12808 && ix86_match_ccmode (insn, CCGOCmode)
12809 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12810 "sar{l}\t{%2, %0|%0, %2}"
12811 [(set_attr "type" "ishift")
12812 (set_attr "mode" "SI")])
12814 (define_insn "*ashrsi3_cmp_zext"
12815 [(set (reg FLAGS_REG)
12817 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12818 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12820 (set (match_operand:DI 0 "register_operand" "=r")
12821 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12823 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12824 && ix86_match_ccmode (insn, CCGOCmode)
12825 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12826 "sar{l}\t{%2, %k0|%k0, %2}"
12827 [(set_attr "type" "ishift")
12828 (set_attr "mode" "SI")])
12830 (define_expand "ashrhi3"
12831 [(set (match_operand:HI 0 "nonimmediate_operand" "")
12832 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12833 (match_operand:QI 2 "nonmemory_operand" "")))]
12834 "TARGET_HIMODE_MATH"
12835 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
12837 (define_insn "*ashrhi3_1_one_bit"
12838 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12839 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12840 (match_operand:QI 2 "const1_operand" "")))
12841 (clobber (reg:CC FLAGS_REG))]
12842 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12843 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12845 [(set_attr "type" "ishift")
12846 (set (attr "length")
12847 (if_then_else (match_operand 0 "register_operand" "")
12849 (const_string "*")))])
12851 (define_insn "*ashrhi3_1"
12852 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12853 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12854 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12855 (clobber (reg:CC FLAGS_REG))]
12856 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12858 sar{w}\t{%2, %0|%0, %2}
12859 sar{w}\t{%b2, %0|%0, %b2}"
12860 [(set_attr "type" "ishift")
12861 (set_attr "mode" "HI")])
12863 ;; This pattern can't accept a variable shift count, since shifts by
12864 ;; zero don't affect the flags. We assume that shifts by constant
12865 ;; zero are optimized away.
12866 (define_insn "*ashrhi3_one_bit_cmp"
12867 [(set (reg FLAGS_REG)
12869 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12870 (match_operand:QI 2 "const1_operand" ""))
12872 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12873 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12874 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12875 && ix86_match_ccmode (insn, CCGOCmode)
12876 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12878 [(set_attr "type" "ishift")
12879 (set (attr "length")
12880 (if_then_else (match_operand 0 "register_operand" "")
12882 (const_string "*")))])
12884 (define_insn "*ashrhi3_one_bit_cconly"
12885 [(set (reg FLAGS_REG)
12887 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12888 (match_operand:QI 2 "const1_operand" ""))
12890 (clobber (match_scratch:HI 0 "=r"))]
12891 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12892 && ix86_match_ccmode (insn, CCGOCmode)
12893 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12895 [(set_attr "type" "ishift")
12896 (set_attr "length" "2")])
12898 ;; This pattern can't accept a variable shift count, since shifts by
12899 ;; zero don't affect the flags. We assume that shifts by constant
12900 ;; zero are optimized away.
12901 (define_insn "*ashrhi3_cmp"
12902 [(set (reg FLAGS_REG)
12904 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12905 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12907 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12908 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12909 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12910 && ix86_match_ccmode (insn, CCGOCmode)
12911 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12912 "sar{w}\t{%2, %0|%0, %2}"
12913 [(set_attr "type" "ishift")
12914 (set_attr "mode" "HI")])
12916 (define_insn "*ashrhi3_cconly"
12917 [(set (reg FLAGS_REG)
12919 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12920 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12922 (clobber (match_scratch:HI 0 "=r"))]
12923 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
12924 && ix86_match_ccmode (insn, CCGOCmode)
12925 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12926 "sar{w}\t{%2, %0|%0, %2}"
12927 [(set_attr "type" "ishift")
12928 (set_attr "mode" "HI")])
12930 (define_expand "ashrqi3"
12931 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12932 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
12933 (match_operand:QI 2 "nonmemory_operand" "")))]
12934 "TARGET_QIMODE_MATH"
12935 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
12937 (define_insn "*ashrqi3_1_one_bit"
12938 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12939 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12940 (match_operand:QI 2 "const1_operand" "")))
12941 (clobber (reg:CC FLAGS_REG))]
12942 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12943 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12945 [(set_attr "type" "ishift")
12946 (set (attr "length")
12947 (if_then_else (match_operand 0 "register_operand" "")
12949 (const_string "*")))])
12951 (define_insn "*ashrqi3_1_one_bit_slp"
12952 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12953 (ashiftrt:QI (match_dup 0)
12954 (match_operand:QI 1 "const1_operand" "")))
12955 (clobber (reg:CC FLAGS_REG))]
12956 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
12957 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
12958 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12960 [(set_attr "type" "ishift1")
12961 (set (attr "length")
12962 (if_then_else (match_operand 0 "register_operand" "")
12964 (const_string "*")))])
12966 (define_insn "*ashrqi3_1"
12967 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12968 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12969 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12970 (clobber (reg:CC FLAGS_REG))]
12971 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12973 sar{b}\t{%2, %0|%0, %2}
12974 sar{b}\t{%b2, %0|%0, %b2}"
12975 [(set_attr "type" "ishift")
12976 (set_attr "mode" "QI")])
12978 (define_insn "*ashrqi3_1_slp"
12979 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12980 (ashiftrt:QI (match_dup 0)
12981 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12982 (clobber (reg:CC FLAGS_REG))]
12983 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
12984 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12986 sar{b}\t{%1, %0|%0, %1}
12987 sar{b}\t{%b1, %0|%0, %b1}"
12988 [(set_attr "type" "ishift1")
12989 (set_attr "mode" "QI")])
12991 ;; This pattern can't accept a variable shift count, since shifts by
12992 ;; zero don't affect the flags. We assume that shifts by constant
12993 ;; zero are optimized away.
12994 (define_insn "*ashrqi3_one_bit_cmp"
12995 [(set (reg FLAGS_REG)
12997 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12998 (match_operand:QI 2 "const1_operand" "I"))
13000 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13001 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
13002 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13003 && ix86_match_ccmode (insn, CCGOCmode)
13004 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
13006 [(set_attr "type" "ishift")
13007 (set (attr "length")
13008 (if_then_else (match_operand 0 "register_operand" "")
13010 (const_string "*")))])
13012 (define_insn "*ashrqi3_one_bit_cconly"
13013 [(set (reg FLAGS_REG)
13015 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13016 (match_operand:QI 2 "const1_operand" ""))
13018 (clobber (match_scratch:QI 0 "=q"))]
13019 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13020 && ix86_match_ccmode (insn, CCGOCmode)
13021 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
13023 [(set_attr "type" "ishift")
13024 (set_attr "length" "2")])
13026 ;; This pattern can't accept a variable shift count, since shifts by
13027 ;; zero don't affect the flags. We assume that shifts by constant
13028 ;; zero are optimized away.
13029 (define_insn "*ashrqi3_cmp"
13030 [(set (reg FLAGS_REG)
13032 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13033 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13035 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13036 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
13037 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13038 && ix86_match_ccmode (insn, CCGOCmode)
13039 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
13040 "sar{b}\t{%2, %0|%0, %2}"
13041 [(set_attr "type" "ishift")
13042 (set_attr "mode" "QI")])
13044 (define_insn "*ashrqi3_cconly"
13045 [(set (reg FLAGS_REG)
13047 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13048 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13050 (clobber (match_scratch:QI 0 "=q"))]
13051 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13052 && ix86_match_ccmode (insn, CCGOCmode)
13053 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
13054 "sar{b}\t{%2, %0|%0, %2}"
13055 [(set_attr "type" "ishift")
13056 (set_attr "mode" "QI")])
13059 ;; Logical shift instructions
13061 ;; See comment above `ashldi3' about how this works.
13063 (define_expand "lshrti3"
13064 [(set (match_operand:TI 0 "register_operand" "")
13065 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
13066 (match_operand:QI 2 "nonmemory_operand" "")))]
13068 "ix86_expand_binary_operator (LSHIFTRT, TImode, operands); DONE;")
13070 ;; This pattern must be defined before *lshrti3_1 to prevent
13071 ;; combine pass from converting sse2_lshrti3 to *lshrti3_1.
13073 (define_insn "*avx_lshrti3"
13074 [(set (match_operand:TI 0 "register_operand" "=x")
13075 (lshiftrt:TI (match_operand:TI 1 "register_operand" "x")
13076 (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
13079 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
13080 return "vpsrldq\t{%2, %1, %0|%0, %1, %2}";
13082 [(set_attr "type" "sseishft")
13083 (set_attr "prefix" "vex")
13084 (set_attr "mode" "TI")])
13086 (define_insn "sse2_lshrti3"
13087 [(set (match_operand:TI 0 "register_operand" "=x")
13088 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
13089 (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
13092 operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
13093 return "psrldq\t{%2, %0|%0, %2}";
13095 [(set_attr "type" "sseishft")
13096 (set_attr "prefix_data16" "1")
13097 (set_attr "mode" "TI")])
13099 (define_insn "*lshrti3_1"
13100 [(set (match_operand:TI 0 "register_operand" "=r")
13101 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
13102 (match_operand:QI 2 "nonmemory_operand" "Oc")))
13103 (clobber (reg:CC FLAGS_REG))]
13106 [(set_attr "type" "multi")])
13109 [(match_scratch:DI 3 "r")
13110 (parallel [(set (match_operand:TI 0 "register_operand" "")
13111 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
13112 (match_operand:QI 2 "nonmemory_operand" "")))
13113 (clobber (reg:CC FLAGS_REG))])
13117 "ix86_split_lshr (operands, operands[3], TImode); DONE;")
13120 [(set (match_operand:TI 0 "register_operand" "")
13121 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
13122 (match_operand:QI 2 "nonmemory_operand" "")))
13123 (clobber (reg:CC FLAGS_REG))]
13124 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
13125 ? epilogue_completed : reload_completed)"
13127 "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;")
13129 (define_expand "lshrdi3"
13130 [(set (match_operand:DI 0 "shiftdi_operand" "")
13131 (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
13132 (match_operand:QI 2 "nonmemory_operand" "")))]
13134 "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
13136 (define_insn "*lshrdi3_1_one_bit_rex64"
13137 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13138 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13139 (match_operand:QI 2 "const1_operand" "")))
13140 (clobber (reg:CC FLAGS_REG))]
13142 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13143 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13145 [(set_attr "type" "ishift")
13146 (set (attr "length")
13147 (if_then_else (match_operand:DI 0 "register_operand" "")
13149 (const_string "*")))])
13151 (define_insn "*lshrdi3_1_rex64"
13152 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13153 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13154 (match_operand:QI 2 "nonmemory_operand" "J,c")))
13155 (clobber (reg:CC FLAGS_REG))]
13156 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13158 shr{q}\t{%2, %0|%0, %2}
13159 shr{q}\t{%b2, %0|%0, %b2}"
13160 [(set_attr "type" "ishift")
13161 (set_attr "mode" "DI")])
13163 ;; This pattern can't accept a variable shift count, since shifts by
13164 ;; zero don't affect the flags. We assume that shifts by constant
13165 ;; zero are optimized away.
13166 (define_insn "*lshrdi3_cmp_one_bit_rex64"
13167 [(set (reg FLAGS_REG)
13169 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13170 (match_operand:QI 2 "const1_operand" ""))
13172 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13173 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
13175 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13176 && ix86_match_ccmode (insn, CCGOCmode)
13177 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13179 [(set_attr "type" "ishift")
13180 (set (attr "length")
13181 (if_then_else (match_operand:DI 0 "register_operand" "")
13183 (const_string "*")))])
13185 (define_insn "*lshrdi3_cconly_one_bit_rex64"
13186 [(set (reg FLAGS_REG)
13188 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13189 (match_operand:QI 2 "const1_operand" ""))
13191 (clobber (match_scratch:DI 0 "=r"))]
13193 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13194 && ix86_match_ccmode (insn, CCGOCmode)
13195 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13197 [(set_attr "type" "ishift")
13198 (set_attr "length" "2")])
13200 ;; This pattern can't accept a variable shift count, since shifts by
13201 ;; zero don't affect the flags. We assume that shifts by constant
13202 ;; zero are optimized away.
13203 (define_insn "*lshrdi3_cmp_rex64"
13204 [(set (reg FLAGS_REG)
13206 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13207 (match_operand:QI 2 "const_1_to_63_operand" "J"))
13209 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13210 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
13212 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13213 && ix86_match_ccmode (insn, CCGOCmode)
13214 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13215 "shr{q}\t{%2, %0|%0, %2}"
13216 [(set_attr "type" "ishift")
13217 (set_attr "mode" "DI")])
13219 (define_insn "*lshrdi3_cconly_rex64"
13220 [(set (reg FLAGS_REG)
13222 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13223 (match_operand:QI 2 "const_1_to_63_operand" "J"))
13225 (clobber (match_scratch:DI 0 "=r"))]
13227 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13228 && ix86_match_ccmode (insn, CCGOCmode)
13229 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13230 "shr{q}\t{%2, %0|%0, %2}"
13231 [(set_attr "type" "ishift")
13232 (set_attr "mode" "DI")])
13234 (define_insn "*lshrdi3_1"
13235 [(set (match_operand:DI 0 "register_operand" "=r")
13236 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
13237 (match_operand:QI 2 "nonmemory_operand" "Jc")))
13238 (clobber (reg:CC FLAGS_REG))]
13241 [(set_attr "type" "multi")])
13243 ;; By default we don't ask for a scratch register, because when DImode
13244 ;; values are manipulated, registers are already at a premium. But if
13245 ;; we have one handy, we won't turn it away.
13247 [(match_scratch:SI 3 "r")
13248 (parallel [(set (match_operand:DI 0 "register_operand" "")
13249 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
13250 (match_operand:QI 2 "nonmemory_operand" "")))
13251 (clobber (reg:CC FLAGS_REG))])
13253 "!TARGET_64BIT && TARGET_CMOVE"
13255 "ix86_split_lshr (operands, operands[3], DImode); DONE;")
13258 [(set (match_operand:DI 0 "register_operand" "")
13259 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
13260 (match_operand:QI 2 "nonmemory_operand" "")))
13261 (clobber (reg:CC FLAGS_REG))]
13262 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
13263 ? epilogue_completed : reload_completed)"
13265 "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;")
13267 (define_expand "lshrsi3"
13268 [(set (match_operand:SI 0 "nonimmediate_operand" "")
13269 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
13270 (match_operand:QI 2 "nonmemory_operand" "")))]
13272 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
13274 (define_insn "*lshrsi3_1_one_bit"
13275 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13276 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13277 (match_operand:QI 2 "const1_operand" "")))
13278 (clobber (reg:CC FLAGS_REG))]
13279 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13280 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13282 [(set_attr "type" "ishift")
13283 (set (attr "length")
13284 (if_then_else (match_operand:SI 0 "register_operand" "")
13286 (const_string "*")))])
13288 (define_insn "*lshrsi3_1_one_bit_zext"
13289 [(set (match_operand:DI 0 "register_operand" "=r")
13290 (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
13291 (match_operand:QI 2 "const1_operand" "")))
13292 (clobber (reg:CC FLAGS_REG))]
13294 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13295 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13297 [(set_attr "type" "ishift")
13298 (set_attr "length" "2")])
13300 (define_insn "*lshrsi3_1"
13301 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13302 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13303 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13304 (clobber (reg:CC FLAGS_REG))]
13305 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13307 shr{l}\t{%2, %0|%0, %2}
13308 shr{l}\t{%b2, %0|%0, %b2}"
13309 [(set_attr "type" "ishift")
13310 (set_attr "mode" "SI")])
13312 (define_insn "*lshrsi3_1_zext"
13313 [(set (match_operand:DI 0 "register_operand" "=r,r")
13315 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13316 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13317 (clobber (reg:CC FLAGS_REG))]
13318 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13320 shr{l}\t{%2, %k0|%k0, %2}
13321 shr{l}\t{%b2, %k0|%k0, %b2}"
13322 [(set_attr "type" "ishift")
13323 (set_attr "mode" "SI")])
13325 ;; This pattern can't accept a variable shift count, since shifts by
13326 ;; zero don't affect the flags. We assume that shifts by constant
13327 ;; zero are optimized away.
13328 (define_insn "*lshrsi3_one_bit_cmp"
13329 [(set (reg FLAGS_REG)
13331 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13332 (match_operand:QI 2 "const1_operand" ""))
13334 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13335 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
13336 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13337 && ix86_match_ccmode (insn, CCGOCmode)
13338 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13340 [(set_attr "type" "ishift")
13341 (set (attr "length")
13342 (if_then_else (match_operand:SI 0 "register_operand" "")
13344 (const_string "*")))])
13346 (define_insn "*lshrsi3_one_bit_cconly"
13347 [(set (reg FLAGS_REG)
13349 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13350 (match_operand:QI 2 "const1_operand" ""))
13352 (clobber (match_scratch:SI 0 "=r"))]
13353 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13354 && ix86_match_ccmode (insn, CCGOCmode)
13355 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13357 [(set_attr "type" "ishift")
13358 (set_attr "length" "2")])
13360 (define_insn "*lshrsi3_cmp_one_bit_zext"
13361 [(set (reg FLAGS_REG)
13363 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
13364 (match_operand:QI 2 "const1_operand" ""))
13366 (set (match_operand:DI 0 "register_operand" "=r")
13367 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
13369 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13370 && ix86_match_ccmode (insn, CCGOCmode)
13371 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13373 [(set_attr "type" "ishift")
13374 (set_attr "length" "2")])
13376 ;; This pattern can't accept a variable shift count, since shifts by
13377 ;; zero don't affect the flags. We assume that shifts by constant
13378 ;; zero are optimized away.
13379 (define_insn "*lshrsi3_cmp"
13380 [(set (reg FLAGS_REG)
13382 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13383 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13385 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13386 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
13387 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13388 && ix86_match_ccmode (insn, CCGOCmode)
13389 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13390 "shr{l}\t{%2, %0|%0, %2}"
13391 [(set_attr "type" "ishift")
13392 (set_attr "mode" "SI")])
13394 (define_insn "*lshrsi3_cconly"
13395 [(set (reg FLAGS_REG)
13397 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13398 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13400 (clobber (match_scratch:SI 0 "=r"))]
13401 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13402 && ix86_match_ccmode (insn, CCGOCmode)
13403 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13404 "shr{l}\t{%2, %0|%0, %2}"
13405 [(set_attr "type" "ishift")
13406 (set_attr "mode" "SI")])
13408 (define_insn "*lshrsi3_cmp_zext"
13409 [(set (reg FLAGS_REG)
13411 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
13412 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13414 (set (match_operand:DI 0 "register_operand" "=r")
13415 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
13417 && (optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13418 && ix86_match_ccmode (insn, CCGOCmode)
13419 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13420 "shr{l}\t{%2, %k0|%k0, %2}"
13421 [(set_attr "type" "ishift")
13422 (set_attr "mode" "SI")])
13424 (define_expand "lshrhi3"
13425 [(set (match_operand:HI 0 "nonimmediate_operand" "")
13426 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
13427 (match_operand:QI 2 "nonmemory_operand" "")))]
13428 "TARGET_HIMODE_MATH"
13429 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
13431 (define_insn "*lshrhi3_1_one_bit"
13432 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13433 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13434 (match_operand:QI 2 "const1_operand" "")))
13435 (clobber (reg:CC FLAGS_REG))]
13436 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13437 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13439 [(set_attr "type" "ishift")
13440 (set (attr "length")
13441 (if_then_else (match_operand 0 "register_operand" "")
13443 (const_string "*")))])
13445 (define_insn "*lshrhi3_1"
13446 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13447 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13448 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13449 (clobber (reg:CC FLAGS_REG))]
13450 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13452 shr{w}\t{%2, %0|%0, %2}
13453 shr{w}\t{%b2, %0|%0, %b2}"
13454 [(set_attr "type" "ishift")
13455 (set_attr "mode" "HI")])
13457 ;; This pattern can't accept a variable shift count, since shifts by
13458 ;; zero don't affect the flags. We assume that shifts by constant
13459 ;; zero are optimized away.
13460 (define_insn "*lshrhi3_one_bit_cmp"
13461 [(set (reg FLAGS_REG)
13463 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13464 (match_operand:QI 2 "const1_operand" ""))
13466 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13467 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
13468 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13469 && ix86_match_ccmode (insn, CCGOCmode)
13470 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13472 [(set_attr "type" "ishift")
13473 (set (attr "length")
13474 (if_then_else (match_operand:SI 0 "register_operand" "")
13476 (const_string "*")))])
13478 (define_insn "*lshrhi3_one_bit_cconly"
13479 [(set (reg FLAGS_REG)
13481 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13482 (match_operand:QI 2 "const1_operand" ""))
13484 (clobber (match_scratch:HI 0 "=r"))]
13485 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13486 && ix86_match_ccmode (insn, CCGOCmode)
13487 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13489 [(set_attr "type" "ishift")
13490 (set_attr "length" "2")])
13492 ;; This pattern can't accept a variable shift count, since shifts by
13493 ;; zero don't affect the flags. We assume that shifts by constant
13494 ;; zero are optimized away.
13495 (define_insn "*lshrhi3_cmp"
13496 [(set (reg FLAGS_REG)
13498 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13499 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13501 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13502 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
13503 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13504 && ix86_match_ccmode (insn, CCGOCmode)
13505 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13506 "shr{w}\t{%2, %0|%0, %2}"
13507 [(set_attr "type" "ishift")
13508 (set_attr "mode" "HI")])
13510 (define_insn "*lshrhi3_cconly"
13511 [(set (reg FLAGS_REG)
13513 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13514 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13516 (clobber (match_scratch:HI 0 "=r"))]
13517 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13518 && ix86_match_ccmode (insn, CCGOCmode)
13519 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13520 "shr{w}\t{%2, %0|%0, %2}"
13521 [(set_attr "type" "ishift")
13522 (set_attr "mode" "HI")])
13524 (define_expand "lshrqi3"
13525 [(set (match_operand:QI 0 "nonimmediate_operand" "")
13526 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
13527 (match_operand:QI 2 "nonmemory_operand" "")))]
13528 "TARGET_QIMODE_MATH"
13529 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
13531 (define_insn "*lshrqi3_1_one_bit"
13532 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13533 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13534 (match_operand:QI 2 "const1_operand" "")))
13535 (clobber (reg:CC FLAGS_REG))]
13536 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13537 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13539 [(set_attr "type" "ishift")
13540 (set (attr "length")
13541 (if_then_else (match_operand 0 "register_operand" "")
13543 (const_string "*")))])
13545 (define_insn "*lshrqi3_1_one_bit_slp"
13546 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13547 (lshiftrt:QI (match_dup 0)
13548 (match_operand:QI 1 "const1_operand" "")))
13549 (clobber (reg:CC FLAGS_REG))]
13550 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
13551 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))"
13553 [(set_attr "type" "ishift1")
13554 (set (attr "length")
13555 (if_then_else (match_operand 0 "register_operand" "")
13557 (const_string "*")))])
13559 (define_insn "*lshrqi3_1"
13560 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13561 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13562 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13563 (clobber (reg:CC FLAGS_REG))]
13564 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13566 shr{b}\t{%2, %0|%0, %2}
13567 shr{b}\t{%b2, %0|%0, %b2}"
13568 [(set_attr "type" "ishift")
13569 (set_attr "mode" "QI")])
13571 (define_insn "*lshrqi3_1_slp"
13572 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13573 (lshiftrt:QI (match_dup 0)
13574 (match_operand:QI 1 "nonmemory_operand" "I,c")))
13575 (clobber (reg:CC FLAGS_REG))]
13576 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
13577 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13579 shr{b}\t{%1, %0|%0, %1}
13580 shr{b}\t{%b1, %0|%0, %b1}"
13581 [(set_attr "type" "ishift1")
13582 (set_attr "mode" "QI")])
13584 ;; This pattern can't accept a variable shift count, since shifts by
13585 ;; zero don't affect the flags. We assume that shifts by constant
13586 ;; zero are optimized away.
13587 (define_insn "*lshrqi2_one_bit_cmp"
13588 [(set (reg FLAGS_REG)
13590 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13591 (match_operand:QI 2 "const1_operand" ""))
13593 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13594 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13595 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13596 && ix86_match_ccmode (insn, CCGOCmode)
13597 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13599 [(set_attr "type" "ishift")
13600 (set (attr "length")
13601 (if_then_else (match_operand:SI 0 "register_operand" "")
13603 (const_string "*")))])
13605 (define_insn "*lshrqi2_one_bit_cconly"
13606 [(set (reg FLAGS_REG)
13608 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13609 (match_operand:QI 2 "const1_operand" ""))
13611 (clobber (match_scratch:QI 0 "=q"))]
13612 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13613 && ix86_match_ccmode (insn, CCGOCmode)
13614 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13616 [(set_attr "type" "ishift")
13617 (set_attr "length" "2")])
13619 ;; This pattern can't accept a variable shift count, since shifts by
13620 ;; zero don't affect the flags. We assume that shifts by constant
13621 ;; zero are optimized away.
13622 (define_insn "*lshrqi2_cmp"
13623 [(set (reg FLAGS_REG)
13625 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13626 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13628 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13629 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13630 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13631 && ix86_match_ccmode (insn, CCGOCmode)
13632 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13633 "shr{b}\t{%2, %0|%0, %2}"
13634 [(set_attr "type" "ishift")
13635 (set_attr "mode" "QI")])
13637 (define_insn "*lshrqi2_cconly"
13638 [(set (reg FLAGS_REG)
13640 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13641 (match_operand:QI 2 "const_1_to_31_operand" "I"))
13643 (clobber (match_scratch:QI 0 "=q"))]
13644 "(optimize_function_for_size_p (cfun) || !TARGET_PARTIAL_FLAG_REG_STALL)
13645 && ix86_match_ccmode (insn, CCGOCmode)
13646 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13647 "shr{b}\t{%2, %0|%0, %2}"
13648 [(set_attr "type" "ishift")
13649 (set_attr "mode" "QI")])
13651 ;; Rotate instructions
13653 (define_expand "rotldi3"
13654 [(set (match_operand:DI 0 "shiftdi_operand" "")
13655 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13656 (match_operand:QI 2 "nonmemory_operand" "")))]
13661 ix86_expand_binary_operator (ROTATE, DImode, operands);
13664 if (!const_1_to_31_operand (operands[2], VOIDmode))
13666 emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2]));
13670 ;; Implement rotation using two double-precision shift instructions
13671 ;; and a scratch register.
13672 (define_insn_and_split "ix86_rotldi3"
13673 [(set (match_operand:DI 0 "register_operand" "=r")
13674 (rotate:DI (match_operand:DI 1 "register_operand" "0")
13675 (match_operand:QI 2 "const_1_to_31_operand" "I")))
13676 (clobber (reg:CC FLAGS_REG))
13677 (clobber (match_scratch:SI 3 "=&r"))]
13680 "&& reload_completed"
13681 [(set (match_dup 3) (match_dup 4))
13683 [(set (match_dup 4)
13684 (ior:SI (ashift:SI (match_dup 4) (match_dup 2))
13685 (lshiftrt:SI (match_dup 5)
13686 (minus:QI (const_int 32) (match_dup 2)))))
13687 (clobber (reg:CC FLAGS_REG))])
13689 [(set (match_dup 5)
13690 (ior:SI (ashift:SI (match_dup 5) (match_dup 2))
13691 (lshiftrt:SI (match_dup 3)
13692 (minus:QI (const_int 32) (match_dup 2)))))
13693 (clobber (reg:CC FLAGS_REG))])]
13694 "split_di (&operands[0], 1, &operands[4], &operands[5]);")
13696 (define_insn "*rotlsi3_1_one_bit_rex64"
13697 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13698 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13699 (match_operand:QI 2 "const1_operand" "")))
13700 (clobber (reg:CC FLAGS_REG))]
13702 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13703 && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13705 [(set_attr "type" "rotate")
13706 (set (attr "length")
13707 (if_then_else (match_operand:DI 0 "register_operand" "")
13709 (const_string "*")))])
13711 (define_insn "*rotldi3_1_rex64"
13712 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13713 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13714 (match_operand:QI 2 "nonmemory_operand" "e,c")))
13715 (clobber (reg:CC FLAGS_REG))]
13716 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13718 rol{q}\t{%2, %0|%0, %2}
13719 rol{q}\t{%b2, %0|%0, %b2}"
13720 [(set_attr "type" "rotate")
13721 (set_attr "mode" "DI")])
13723 (define_expand "rotlsi3"
13724 [(set (match_operand:SI 0 "nonimmediate_operand" "")
13725 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
13726 (match_operand:QI 2 "nonmemory_operand" "")))]
13728 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
13730 (define_insn "*rotlsi3_1_one_bit"
13731 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13732 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13733 (match_operand:QI 2 "const1_operand" "")))
13734 (clobber (reg:CC FLAGS_REG))]
13735 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13736 && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13738 [(set_attr "type" "rotate")
13739 (set (attr "length")
13740 (if_then_else (match_operand:SI 0 "register_operand" "")
13742 (const_string "*")))])
13744 (define_insn "*rotlsi3_1_one_bit_zext"
13745 [(set (match_operand:DI 0 "register_operand" "=r")
13747 (rotate:SI (match_operand:SI 1 "register_operand" "0")
13748 (match_operand:QI 2 "const1_operand" ""))))
13749 (clobber (reg:CC FLAGS_REG))]
13751 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13752 && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13754 [(set_attr "type" "rotate")
13755 (set_attr "length" "2")])
13757 (define_insn "*rotlsi3_1"
13758 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13759 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13760 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13761 (clobber (reg:CC FLAGS_REG))]
13762 "ix86_binary_operator_ok (ROTATE, SImode, operands)"
13764 rol{l}\t{%2, %0|%0, %2}
13765 rol{l}\t{%b2, %0|%0, %b2}"
13766 [(set_attr "type" "rotate")
13767 (set_attr "mode" "SI")])
13769 (define_insn "*rotlsi3_1_zext"
13770 [(set (match_operand:DI 0 "register_operand" "=r,r")
13772 (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
13773 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13774 (clobber (reg:CC FLAGS_REG))]
13775 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13777 rol{l}\t{%2, %k0|%k0, %2}
13778 rol{l}\t{%b2, %k0|%k0, %b2}"
13779 [(set_attr "type" "rotate")
13780 (set_attr "mode" "SI")])
13782 (define_expand "rotlhi3"
13783 [(set (match_operand:HI 0 "nonimmediate_operand" "")
13784 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
13785 (match_operand:QI 2 "nonmemory_operand" "")))]
13786 "TARGET_HIMODE_MATH"
13787 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
13789 (define_insn "*rotlhi3_1_one_bit"
13790 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13791 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13792 (match_operand:QI 2 "const1_operand" "")))
13793 (clobber (reg:CC FLAGS_REG))]
13794 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13795 && ix86_binary_operator_ok (ROTATE, HImode, operands)"
13797 [(set_attr "type" "rotate")
13798 (set (attr "length")
13799 (if_then_else (match_operand 0 "register_operand" "")
13801 (const_string "*")))])
13803 (define_insn "*rotlhi3_1"
13804 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13805 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13806 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13807 (clobber (reg:CC FLAGS_REG))]
13808 "ix86_binary_operator_ok (ROTATE, HImode, operands)"
13810 rol{w}\t{%2, %0|%0, %2}
13811 rol{w}\t{%b2, %0|%0, %b2}"
13812 [(set_attr "type" "rotate")
13813 (set_attr "mode" "HI")])
13816 [(set (match_operand:HI 0 "register_operand" "")
13817 (rotate:HI (match_dup 0) (const_int 8)))
13818 (clobber (reg:CC FLAGS_REG))]
13820 [(parallel [(set (strict_low_part (match_dup 0))
13821 (bswap:HI (match_dup 0)))
13822 (clobber (reg:CC FLAGS_REG))])]
13825 (define_expand "rotlqi3"
13826 [(set (match_operand:QI 0 "nonimmediate_operand" "")
13827 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
13828 (match_operand:QI 2 "nonmemory_operand" "")))]
13829 "TARGET_QIMODE_MATH"
13830 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
13832 (define_insn "*rotlqi3_1_one_bit_slp"
13833 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13834 (rotate:QI (match_dup 0)
13835 (match_operand:QI 1 "const1_operand" "")))
13836 (clobber (reg:CC FLAGS_REG))]
13837 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
13838 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))"
13840 [(set_attr "type" "rotate1")
13841 (set (attr "length")
13842 (if_then_else (match_operand 0 "register_operand" "")
13844 (const_string "*")))])
13846 (define_insn "*rotlqi3_1_one_bit"
13847 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13848 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13849 (match_operand:QI 2 "const1_operand" "")))
13850 (clobber (reg:CC FLAGS_REG))]
13851 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13852 && ix86_binary_operator_ok (ROTATE, QImode, operands)"
13854 [(set_attr "type" "rotate")
13855 (set (attr "length")
13856 (if_then_else (match_operand 0 "register_operand" "")
13858 (const_string "*")))])
13860 (define_insn "*rotlqi3_1_slp"
13861 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13862 (rotate:QI (match_dup 0)
13863 (match_operand:QI 1 "nonmemory_operand" "I,c")))
13864 (clobber (reg:CC FLAGS_REG))]
13865 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
13866 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13868 rol{b}\t{%1, %0|%0, %1}
13869 rol{b}\t{%b1, %0|%0, %b1}"
13870 [(set_attr "type" "rotate1")
13871 (set_attr "mode" "QI")])
13873 (define_insn "*rotlqi3_1"
13874 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13875 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13876 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13877 (clobber (reg:CC FLAGS_REG))]
13878 "ix86_binary_operator_ok (ROTATE, QImode, operands)"
13880 rol{b}\t{%2, %0|%0, %2}
13881 rol{b}\t{%b2, %0|%0, %b2}"
13882 [(set_attr "type" "rotate")
13883 (set_attr "mode" "QI")])
13885 (define_expand "rotrdi3"
13886 [(set (match_operand:DI 0 "shiftdi_operand" "")
13887 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13888 (match_operand:QI 2 "nonmemory_operand" "")))]
13893 ix86_expand_binary_operator (ROTATERT, DImode, operands);
13896 if (!const_1_to_31_operand (operands[2], VOIDmode))
13898 emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2]));
13902 ;; Implement rotation using two double-precision shift instructions
13903 ;; and a scratch register.
13904 (define_insn_and_split "ix86_rotrdi3"
13905 [(set (match_operand:DI 0 "register_operand" "=r")
13906 (rotatert:DI (match_operand:DI 1 "register_operand" "0")
13907 (match_operand:QI 2 "const_1_to_31_operand" "I")))
13908 (clobber (reg:CC FLAGS_REG))
13909 (clobber (match_scratch:SI 3 "=&r"))]
13912 "&& reload_completed"
13913 [(set (match_dup 3) (match_dup 4))
13915 [(set (match_dup 4)
13916 (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2))
13917 (ashift:SI (match_dup 5)
13918 (minus:QI (const_int 32) (match_dup 2)))))
13919 (clobber (reg:CC FLAGS_REG))])
13921 [(set (match_dup 5)
13922 (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2))
13923 (ashift:SI (match_dup 3)
13924 (minus:QI (const_int 32) (match_dup 2)))))
13925 (clobber (reg:CC FLAGS_REG))])]
13926 "split_di (&operands[0], 1, &operands[4], &operands[5]);")
13928 (define_insn "*rotrdi3_1_one_bit_rex64"
13929 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13930 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13931 (match_operand:QI 2 "const1_operand" "")))
13932 (clobber (reg:CC FLAGS_REG))]
13934 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13935 && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13937 [(set_attr "type" "rotate")
13938 (set (attr "length")
13939 (if_then_else (match_operand:DI 0 "register_operand" "")
13941 (const_string "*")))])
13943 (define_insn "*rotrdi3_1_rex64"
13944 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13945 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13946 (match_operand:QI 2 "nonmemory_operand" "J,c")))
13947 (clobber (reg:CC FLAGS_REG))]
13948 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13950 ror{q}\t{%2, %0|%0, %2}
13951 ror{q}\t{%b2, %0|%0, %b2}"
13952 [(set_attr "type" "rotate")
13953 (set_attr "mode" "DI")])
13955 (define_expand "rotrsi3"
13956 [(set (match_operand:SI 0 "nonimmediate_operand" "")
13957 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
13958 (match_operand:QI 2 "nonmemory_operand" "")))]
13960 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
13962 (define_insn "*rotrsi3_1_one_bit"
13963 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13964 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13965 (match_operand:QI 2 "const1_operand" "")))
13966 (clobber (reg:CC FLAGS_REG))]
13967 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13968 && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13970 [(set_attr "type" "rotate")
13971 (set (attr "length")
13972 (if_then_else (match_operand:SI 0 "register_operand" "")
13974 (const_string "*")))])
13976 (define_insn "*rotrsi3_1_one_bit_zext"
13977 [(set (match_operand:DI 0 "register_operand" "=r")
13979 (rotatert:SI (match_operand:SI 1 "register_operand" "0")
13980 (match_operand:QI 2 "const1_operand" ""))))
13981 (clobber (reg:CC FLAGS_REG))]
13983 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
13984 && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13986 [(set_attr "type" "rotate")
13987 (set (attr "length")
13988 (if_then_else (match_operand:SI 0 "register_operand" "")
13990 (const_string "*")))])
13992 (define_insn "*rotrsi3_1"
13993 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13994 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13995 (match_operand:QI 2 "nonmemory_operand" "I,c")))
13996 (clobber (reg:CC FLAGS_REG))]
13997 "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13999 ror{l}\t{%2, %0|%0, %2}
14000 ror{l}\t{%b2, %0|%0, %b2}"
14001 [(set_attr "type" "rotate")
14002 (set_attr "mode" "SI")])
14004 (define_insn "*rotrsi3_1_zext"
14005 [(set (match_operand:DI 0 "register_operand" "=r,r")
14007 (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
14008 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
14009 (clobber (reg:CC FLAGS_REG))]
14010 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
14012 ror{l}\t{%2, %k0|%k0, %2}
14013 ror{l}\t{%b2, %k0|%k0, %b2}"
14014 [(set_attr "type" "rotate")
14015 (set_attr "mode" "SI")])
14017 (define_expand "rotrhi3"
14018 [(set (match_operand:HI 0 "nonimmediate_operand" "")
14019 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
14020 (match_operand:QI 2 "nonmemory_operand" "")))]
14021 "TARGET_HIMODE_MATH"
14022 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
14024 (define_insn "*rotrhi3_one_bit"
14025 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
14026 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
14027 (match_operand:QI 2 "const1_operand" "")))
14028 (clobber (reg:CC FLAGS_REG))]
14029 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
14030 && ix86_binary_operator_ok (ROTATERT, HImode, operands)"
14032 [(set_attr "type" "rotate")
14033 (set (attr "length")
14034 (if_then_else (match_operand 0 "register_operand" "")
14036 (const_string "*")))])
14038 (define_insn "*rotrhi3_1"
14039 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
14040 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
14041 (match_operand:QI 2 "nonmemory_operand" "I,c")))
14042 (clobber (reg:CC FLAGS_REG))]
14043 "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
14045 ror{w}\t{%2, %0|%0, %2}
14046 ror{w}\t{%b2, %0|%0, %b2}"
14047 [(set_attr "type" "rotate")
14048 (set_attr "mode" "HI")])
14051 [(set (match_operand:HI 0 "register_operand" "")
14052 (rotatert:HI (match_dup 0) (const_int 8)))
14053 (clobber (reg:CC FLAGS_REG))]
14055 [(parallel [(set (strict_low_part (match_dup 0))
14056 (bswap:HI (match_dup 0)))
14057 (clobber (reg:CC FLAGS_REG))])]
14060 (define_expand "rotrqi3"
14061 [(set (match_operand:QI 0 "nonimmediate_operand" "")
14062 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
14063 (match_operand:QI 2 "nonmemory_operand" "")))]
14064 "TARGET_QIMODE_MATH"
14065 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
14067 (define_insn "*rotrqi3_1_one_bit"
14068 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
14069 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
14070 (match_operand:QI 2 "const1_operand" "")))
14071 (clobber (reg:CC FLAGS_REG))]
14072 "(TARGET_SHIFT1 || optimize_function_for_size_p (cfun))
14073 && ix86_binary_operator_ok (ROTATERT, QImode, operands)"
14075 [(set_attr "type" "rotate")
14076 (set (attr "length")
14077 (if_then_else (match_operand 0 "register_operand" "")
14079 (const_string "*")))])
14081 (define_insn "*rotrqi3_1_one_bit_slp"
14082 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
14083 (rotatert:QI (match_dup 0)
14084 (match_operand:QI 1 "const1_operand" "")))
14085 (clobber (reg:CC FLAGS_REG))]
14086 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
14087 && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun))"
14089 [(set_attr "type" "rotate1")
14090 (set (attr "length")
14091 (if_then_else (match_operand 0 "register_operand" "")
14093 (const_string "*")))])
14095 (define_insn "*rotrqi3_1"
14096 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
14097 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
14098 (match_operand:QI 2 "nonmemory_operand" "I,c")))
14099 (clobber (reg:CC FLAGS_REG))]
14100 "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
14102 ror{b}\t{%2, %0|%0, %2}
14103 ror{b}\t{%b2, %0|%0, %b2}"
14104 [(set_attr "type" "rotate")
14105 (set_attr "mode" "QI")])
14107 (define_insn "*rotrqi3_1_slp"
14108 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
14109 (rotatert:QI (match_dup 0)
14110 (match_operand:QI 1 "nonmemory_operand" "I,c")))
14111 (clobber (reg:CC FLAGS_REG))]
14112 "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
14113 && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
14115 ror{b}\t{%1, %0|%0, %1}
14116 ror{b}\t{%b1, %0|%0, %b1}"
14117 [(set_attr "type" "rotate1")
14118 (set_attr "mode" "QI")])
14120 ;; Bit set / bit test instructions
14122 (define_expand "extv"
14123 [(set (match_operand:SI 0 "register_operand" "")
14124 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
14125 (match_operand:SI 2 "const8_operand" "")
14126 (match_operand:SI 3 "const8_operand" "")))]
14129 /* Handle extractions from %ah et al. */
14130 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
14133 /* From mips.md: extract_bit_field doesn't verify that our source
14134 matches the predicate, so check it again here. */
14135 if (! ext_register_operand (operands[1], VOIDmode))
14139 (define_expand "extzv"
14140 [(set (match_operand:SI 0 "register_operand" "")
14141 (zero_extract:SI (match_operand 1 "ext_register_operand" "")
14142 (match_operand:SI 2 "const8_operand" "")
14143 (match_operand:SI 3 "const8_operand" "")))]
14146 /* Handle extractions from %ah et al. */
14147 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
14150 /* From mips.md: extract_bit_field doesn't verify that our source
14151 matches the predicate, so check it again here. */
14152 if (! ext_register_operand (operands[1], VOIDmode))
14156 (define_expand "insv"
14157 [(set (zero_extract (match_operand 0 "ext_register_operand" "")
14158 (match_operand 1 "const8_operand" "")
14159 (match_operand 2 "const8_operand" ""))
14160 (match_operand 3 "register_operand" ""))]
14163 /* Handle insertions to %ah et al. */
14164 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
14167 /* From mips.md: insert_bit_field doesn't verify that our source
14168 matches the predicate, so check it again here. */
14169 if (! ext_register_operand (operands[0], VOIDmode))
14173 emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
14175 emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
14180 ;; %%% bts, btr, btc, bt.
14181 ;; In general these instructions are *slow* when applied to memory,
14182 ;; since they enforce atomic operation. When applied to registers,
14183 ;; it depends on the cpu implementation. They're never faster than
14184 ;; the corresponding and/ior/xor operations, so with 32-bit there's
14185 ;; no point. But in 64-bit, we can't hold the relevant immediates
14186 ;; within the instruction itself, so operating on bits in the high
14187 ;; 32-bits of a register becomes easier.
14189 ;; These are slow on Nocona, but fast on Athlon64. We do require the use
14190 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
14191 ;; negdf respectively, so they can never be disabled entirely.
14193 (define_insn "*btsq"
14194 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
14196 (match_operand:DI 1 "const_0_to_63_operand" ""))
14198 (clobber (reg:CC FLAGS_REG))]
14199 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
14200 "bts{q}\t{%1, %0|%0, %1}"
14201 [(set_attr "type" "alu1")])
14203 (define_insn "*btrq"
14204 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
14206 (match_operand:DI 1 "const_0_to_63_operand" ""))
14208 (clobber (reg:CC FLAGS_REG))]
14209 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
14210 "btr{q}\t{%1, %0|%0, %1}"
14211 [(set_attr "type" "alu1")])
14213 (define_insn "*btcq"
14214 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
14216 (match_operand:DI 1 "const_0_to_63_operand" ""))
14217 (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
14218 (clobber (reg:CC FLAGS_REG))]
14219 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
14220 "btc{q}\t{%1, %0|%0, %1}"
14221 [(set_attr "type" "alu1")])
14223 ;; Allow Nocona to avoid these instructions if a register is available.
14226 [(match_scratch:DI 2 "r")
14227 (parallel [(set (zero_extract:DI
14228 (match_operand:DI 0 "register_operand" "")
14230 (match_operand:DI 1 "const_0_to_63_operand" ""))
14232 (clobber (reg:CC FLAGS_REG))])]
14233 "TARGET_64BIT && !TARGET_USE_BT"
14236 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
14239 if (HOST_BITS_PER_WIDE_INT >= 64)
14240 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14241 else if (i < HOST_BITS_PER_WIDE_INT)
14242 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14244 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
14246 op1 = immed_double_const (lo, hi, DImode);
14249 emit_move_insn (operands[2], op1);
14253 emit_insn (gen_iordi3 (operands[0], operands[0], op1));
14258 [(match_scratch:DI 2 "r")
14259 (parallel [(set (zero_extract:DI
14260 (match_operand:DI 0 "register_operand" "")
14262 (match_operand:DI 1 "const_0_to_63_operand" ""))
14264 (clobber (reg:CC FLAGS_REG))])]
14265 "TARGET_64BIT && !TARGET_USE_BT"
14268 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
14271 if (HOST_BITS_PER_WIDE_INT >= 64)
14272 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14273 else if (i < HOST_BITS_PER_WIDE_INT)
14274 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14276 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
14278 op1 = immed_double_const (~lo, ~hi, DImode);
14281 emit_move_insn (operands[2], op1);
14285 emit_insn (gen_anddi3 (operands[0], operands[0], op1));
14290 [(match_scratch:DI 2 "r")
14291 (parallel [(set (zero_extract:DI
14292 (match_operand:DI 0 "register_operand" "")
14294 (match_operand:DI 1 "const_0_to_63_operand" ""))
14295 (not:DI (zero_extract:DI
14296 (match_dup 0) (const_int 1) (match_dup 1))))
14297 (clobber (reg:CC FLAGS_REG))])]
14298 "TARGET_64BIT && !TARGET_USE_BT"
14301 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
14304 if (HOST_BITS_PER_WIDE_INT >= 64)
14305 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14306 else if (i < HOST_BITS_PER_WIDE_INT)
14307 lo = (HOST_WIDE_INT)1 << i, hi = 0;
14309 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
14311 op1 = immed_double_const (lo, hi, DImode);
14314 emit_move_insn (operands[2], op1);
14318 emit_insn (gen_xordi3 (operands[0], operands[0], op1));
14322 (define_insn "*btdi_rex64"
14323 [(set (reg:CCC FLAGS_REG)
14326 (match_operand:DI 0 "register_operand" "r")
14328 (match_operand:DI 1 "nonmemory_operand" "rN"))
14330 "TARGET_64BIT && (TARGET_USE_BT || optimize_function_for_size_p (cfun))"
14331 "bt{q}\t{%1, %0|%0, %1}"
14332 [(set_attr "type" "alu1")])
14334 (define_insn "*btsi"
14335 [(set (reg:CCC FLAGS_REG)
14338 (match_operand:SI 0 "register_operand" "r")
14340 (match_operand:SI 1 "nonmemory_operand" "rN"))
14342 "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
14343 "bt{l}\t{%1, %0|%0, %1}"
14344 [(set_attr "type" "alu1")])
14346 ;; Store-flag instructions.
14348 ;; For all sCOND expanders, also expand the compare or test insn that
14349 ;; generates cc0. Generate an equality comparison if `seq' or `sne'.
14351 ;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way
14352 ;; to avoid partial register stalls. Otherwise do things the setcc+movzx
14353 ;; way, which can later delete the movzx if only QImode is needed.
14355 (define_insn "*setcc_1"
14356 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
14357 (match_operator:QI 1 "ix86_comparison_operator"
14358 [(reg FLAGS_REG) (const_int 0)]))]
14361 [(set_attr "type" "setcc")
14362 (set_attr "mode" "QI")])
14364 (define_insn "*setcc_2"
14365 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
14366 (match_operator:QI 1 "ix86_comparison_operator"
14367 [(reg FLAGS_REG) (const_int 0)]))]
14370 [(set_attr "type" "setcc")
14371 (set_attr "mode" "QI")])
14373 ;; In general it is not safe to assume too much about CCmode registers,
14374 ;; so simplify-rtx stops when it sees a second one. Under certain
14375 ;; conditions this is safe on x86, so help combine not create
14382 [(set (match_operand:QI 0 "nonimmediate_operand" "")
14383 (ne:QI (match_operator 1 "ix86_comparison_operator"
14384 [(reg FLAGS_REG) (const_int 0)])
14387 [(set (match_dup 0) (match_dup 1))]
14389 PUT_MODE (operands[1], QImode);
14393 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
14394 (ne:QI (match_operator 1 "ix86_comparison_operator"
14395 [(reg FLAGS_REG) (const_int 0)])
14398 [(set (match_dup 0) (match_dup 1))]
14400 PUT_MODE (operands[1], QImode);
14404 [(set (match_operand:QI 0 "nonimmediate_operand" "")
14405 (eq:QI (match_operator 1 "ix86_comparison_operator"
14406 [(reg FLAGS_REG) (const_int 0)])
14409 [(set (match_dup 0) (match_dup 1))]
14411 rtx new_op1 = copy_rtx (operands[1]);
14412 operands[1] = new_op1;
14413 PUT_MODE (new_op1, QImode);
14414 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
14415 GET_MODE (XEXP (new_op1, 0))));
14417 /* Make sure that (a) the CCmode we have for the flags is strong
14418 enough for the reversed compare or (b) we have a valid FP compare. */
14419 if (! ix86_comparison_operator (new_op1, VOIDmode))
14424 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
14425 (eq:QI (match_operator 1 "ix86_comparison_operator"
14426 [(reg FLAGS_REG) (const_int 0)])
14429 [(set (match_dup 0) (match_dup 1))]
14431 rtx new_op1 = copy_rtx (operands[1]);
14432 operands[1] = new_op1;
14433 PUT_MODE (new_op1, QImode);
14434 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
14435 GET_MODE (XEXP (new_op1, 0))));
14437 /* Make sure that (a) the CCmode we have for the flags is strong
14438 enough for the reversed compare or (b) we have a valid FP compare. */
14439 if (! ix86_comparison_operator (new_op1, VOIDmode))
14443 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
14444 ;; subsequent logical operations are used to imitate conditional moves.
14445 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
14448 (define_insn "*avx_setcc<mode>"
14449 [(set (match_operand:MODEF 0 "register_operand" "=x")
14450 (match_operator:MODEF 1 "avx_comparison_float_operator"
14451 [(match_operand:MODEF 2 "register_operand" "x")
14452 (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
14454 "vcmp%D1s<ssemodefsuffix>\t{%3, %2, %0|%0, %2, %3}"
14455 [(set_attr "type" "ssecmp")
14456 (set_attr "prefix" "vex")
14457 (set_attr "mode" "<MODE>")])
14459 (define_insn "*sse_setcc<mode>"
14460 [(set (match_operand:MODEF 0 "register_operand" "=x")
14461 (match_operator:MODEF 1 "sse_comparison_operator"
14462 [(match_operand:MODEF 2 "register_operand" "0")
14463 (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
14464 "SSE_FLOAT_MODE_P (<MODE>mode) && !TARGET_SSE5"
14465 "cmp%D1s<ssemodefsuffix>\t{%3, %0|%0, %3}"
14466 [(set_attr "type" "ssecmp")
14467 (set_attr "mode" "<MODE>")])
14469 (define_insn "*sse5_setcc<mode>"
14470 [(set (match_operand:MODEF 0 "register_operand" "=x")
14471 (match_operator:MODEF 1 "sse5_comparison_float_operator"
14472 [(match_operand:MODEF 2 "register_operand" "x")
14473 (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
14475 "com%Y1s<ssemodefsuffix>\t{%3, %2, %0|%0, %2, %3}"
14476 [(set_attr "type" "sse4arg")
14477 (set_attr "mode" "<MODE>")])
14480 ;; Basic conditional jump instructions.
14481 ;; We ignore the overflow flag for signed branch instructions.
14483 (define_insn "*jcc_1"
14485 (if_then_else (match_operator 1 "ix86_comparison_operator"
14486 [(reg FLAGS_REG) (const_int 0)])
14487 (label_ref (match_operand 0 "" ""))
14491 [(set_attr "type" "ibr")
14492 (set_attr "modrm" "0")
14493 (set (attr "length")
14494 (if_then_else (and (ge (minus (match_dup 0) (pc))
14496 (lt (minus (match_dup 0) (pc))
14501 (define_insn "*jcc_2"
14503 (if_then_else (match_operator 1 "ix86_comparison_operator"
14504 [(reg FLAGS_REG) (const_int 0)])
14506 (label_ref (match_operand 0 "" ""))))]
14509 [(set_attr "type" "ibr")
14510 (set_attr "modrm" "0")
14511 (set (attr "length")
14512 (if_then_else (and (ge (minus (match_dup 0) (pc))
14514 (lt (minus (match_dup 0) (pc))
14519 ;; In general it is not safe to assume too much about CCmode registers,
14520 ;; so simplify-rtx stops when it sees a second one. Under certain
14521 ;; conditions this is safe on x86, so help combine not create
14529 (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
14530 [(reg FLAGS_REG) (const_int 0)])
14532 (label_ref (match_operand 1 "" ""))
14536 (if_then_else (match_dup 0)
14537 (label_ref (match_dup 1))
14540 PUT_MODE (operands[0], VOIDmode);
14545 (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
14546 [(reg FLAGS_REG) (const_int 0)])
14548 (label_ref (match_operand 1 "" ""))
14552 (if_then_else (match_dup 0)
14553 (label_ref (match_dup 1))
14556 rtx new_op0 = copy_rtx (operands[0]);
14557 operands[0] = new_op0;
14558 PUT_MODE (new_op0, VOIDmode);
14559 PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
14560 GET_MODE (XEXP (new_op0, 0))));
14562 /* Make sure that (a) the CCmode we have for the flags is strong
14563 enough for the reversed compare or (b) we have a valid FP compare. */
14564 if (! ix86_comparison_operator (new_op0, VOIDmode))
14568 ;; zero_extend in SImode is correct, since this is what combine pass
14569 ;; generates from shift insn with QImode operand. Actually, the mode of
14570 ;; operand 2 (bit offset operand) doesn't matter since bt insn takes
14571 ;; appropriate modulo of the bit offset value.
14573 (define_insn_and_split "*jcc_btdi_rex64"
14575 (if_then_else (match_operator 0 "bt_comparison_operator"
14577 (match_operand:DI 1 "register_operand" "r")
14580 (match_operand:QI 2 "register_operand" "r")))
14582 (label_ref (match_operand 3 "" ""))
14584 (clobber (reg:CC FLAGS_REG))]
14585 "TARGET_64BIT && (TARGET_USE_BT || optimize_function_for_size_p (cfun))"
14588 [(set (reg:CCC FLAGS_REG)
14596 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14597 (label_ref (match_dup 3))
14600 operands[2] = simplify_gen_subreg (DImode, operands[2], QImode, 0);
14602 PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14605 ;; avoid useless masking of bit offset operand
14606 (define_insn_and_split "*jcc_btdi_mask_rex64"
14608 (if_then_else (match_operator 0 "bt_comparison_operator"
14610 (match_operand:DI 1 "register_operand" "r")
14613 (match_operand:SI 2 "register_operand" "r")
14614 (match_operand:SI 3 "const_int_operand" "n")))])
14615 (label_ref (match_operand 4 "" ""))
14617 (clobber (reg:CC FLAGS_REG))]
14618 "TARGET_64BIT && (TARGET_USE_BT || optimize_function_for_size_p (cfun))
14619 && (INTVAL (operands[3]) & 0x3f) == 0x3f"
14622 [(set (reg:CCC FLAGS_REG)
14630 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14631 (label_ref (match_dup 4))
14634 operands[2] = simplify_gen_subreg (DImode, operands[2], SImode, 0);
14636 PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14639 (define_insn_and_split "*jcc_btsi"
14641 (if_then_else (match_operator 0 "bt_comparison_operator"
14643 (match_operand:SI 1 "register_operand" "r")
14646 (match_operand:QI 2 "register_operand" "r")))
14648 (label_ref (match_operand 3 "" ""))
14650 (clobber (reg:CC FLAGS_REG))]
14651 "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
14654 [(set (reg:CCC FLAGS_REG)
14662 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14663 (label_ref (match_dup 3))
14666 operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
14668 PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14671 ;; avoid useless masking of bit offset operand
14672 (define_insn_and_split "*jcc_btsi_mask"
14674 (if_then_else (match_operator 0 "bt_comparison_operator"
14676 (match_operand:SI 1 "register_operand" "r")
14679 (match_operand:SI 2 "register_operand" "r")
14680 (match_operand:SI 3 "const_int_operand" "n")))])
14681 (label_ref (match_operand 4 "" ""))
14683 (clobber (reg:CC FLAGS_REG))]
14684 "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
14685 && (INTVAL (operands[3]) & 0x1f) == 0x1f"
14688 [(set (reg:CCC FLAGS_REG)
14696 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14697 (label_ref (match_dup 4))
14699 "PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));")
14701 (define_insn_and_split "*jcc_btsi_1"
14703 (if_then_else (match_operator 0 "bt_comparison_operator"
14706 (match_operand:SI 1 "register_operand" "r")
14707 (match_operand:QI 2 "register_operand" "r"))
14710 (label_ref (match_operand 3 "" ""))
14712 (clobber (reg:CC FLAGS_REG))]
14713 "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
14716 [(set (reg:CCC FLAGS_REG)
14724 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14725 (label_ref (match_dup 3))
14728 operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
14730 PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14733 ;; avoid useless masking of bit offset operand
14734 (define_insn_and_split "*jcc_btsi_mask_1"
14737 (match_operator 0 "bt_comparison_operator"
14740 (match_operand:SI 1 "register_operand" "r")
14743 (match_operand:SI 2 "register_operand" "r")
14744 (match_operand:SI 3 "const_int_operand" "n")) 0))
14747 (label_ref (match_operand 4 "" ""))
14749 (clobber (reg:CC FLAGS_REG))]
14750 "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
14751 && (INTVAL (operands[3]) & 0x1f) == 0x1f"
14754 [(set (reg:CCC FLAGS_REG)
14762 (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14763 (label_ref (match_dup 4))
14765 "PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));")
14767 ;; Define combination compare-and-branch fp compare instructions to use
14768 ;; during early optimization. Splitting the operation apart early makes
14769 ;; for bad code when we want to reverse the operation.
14771 (define_insn "*fp_jcc_1_mixed"
14773 (if_then_else (match_operator 0 "comparison_operator"
14774 [(match_operand 1 "register_operand" "f,x")
14775 (match_operand 2 "nonimmediate_operand" "f,xm")])
14776 (label_ref (match_operand 3 "" ""))
14778 (clobber (reg:CCFP FPSR_REG))
14779 (clobber (reg:CCFP FLAGS_REG))]
14780 "TARGET_MIX_SSE_I387
14781 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14782 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14783 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14786 (define_insn "*fp_jcc_1_sse"
14788 (if_then_else (match_operator 0 "comparison_operator"
14789 [(match_operand 1 "register_operand" "x")
14790 (match_operand 2 "nonimmediate_operand" "xm")])
14791 (label_ref (match_operand 3 "" ""))
14793 (clobber (reg:CCFP FPSR_REG))
14794 (clobber (reg:CCFP FLAGS_REG))]
14796 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14797 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14798 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14801 (define_insn "*fp_jcc_1_387"
14803 (if_then_else (match_operator 0 "comparison_operator"
14804 [(match_operand 1 "register_operand" "f")
14805 (match_operand 2 "register_operand" "f")])
14806 (label_ref (match_operand 3 "" ""))
14808 (clobber (reg:CCFP FPSR_REG))
14809 (clobber (reg:CCFP FLAGS_REG))]
14810 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14812 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14813 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14816 (define_insn "*fp_jcc_2_mixed"
14818 (if_then_else (match_operator 0 "comparison_operator"
14819 [(match_operand 1 "register_operand" "f,x")
14820 (match_operand 2 "nonimmediate_operand" "f,xm")])
14822 (label_ref (match_operand 3 "" ""))))
14823 (clobber (reg:CCFP FPSR_REG))
14824 (clobber (reg:CCFP FLAGS_REG))]
14825 "TARGET_MIX_SSE_I387
14826 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14827 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14828 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14831 (define_insn "*fp_jcc_2_sse"
14833 (if_then_else (match_operator 0 "comparison_operator"
14834 [(match_operand 1 "register_operand" "x")
14835 (match_operand 2 "nonimmediate_operand" "xm")])
14837 (label_ref (match_operand 3 "" ""))))
14838 (clobber (reg:CCFP FPSR_REG))
14839 (clobber (reg:CCFP FLAGS_REG))]
14841 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14842 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14843 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14846 (define_insn "*fp_jcc_2_387"
14848 (if_then_else (match_operator 0 "comparison_operator"
14849 [(match_operand 1 "register_operand" "f")
14850 (match_operand 2 "register_operand" "f")])
14852 (label_ref (match_operand 3 "" ""))))
14853 (clobber (reg:CCFP FPSR_REG))
14854 (clobber (reg:CCFP FLAGS_REG))]
14855 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14857 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14858 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14861 (define_insn "*fp_jcc_3_387"
14863 (if_then_else (match_operator 0 "comparison_operator"
14864 [(match_operand 1 "register_operand" "f")
14865 (match_operand 2 "nonimmediate_operand" "fm")])
14866 (label_ref (match_operand 3 "" ""))
14868 (clobber (reg:CCFP FPSR_REG))
14869 (clobber (reg:CCFP FLAGS_REG))
14870 (clobber (match_scratch:HI 4 "=a"))]
14872 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14873 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14874 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14875 && SELECT_CC_MODE (GET_CODE (operands[0]),
14876 operands[1], operands[2]) == CCFPmode
14877 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14880 (define_insn "*fp_jcc_4_387"
14882 (if_then_else (match_operator 0 "comparison_operator"
14883 [(match_operand 1 "register_operand" "f")
14884 (match_operand 2 "nonimmediate_operand" "fm")])
14886 (label_ref (match_operand 3 "" ""))))
14887 (clobber (reg:CCFP FPSR_REG))
14888 (clobber (reg:CCFP FLAGS_REG))
14889 (clobber (match_scratch:HI 4 "=a"))]
14891 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14892 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14893 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14894 && SELECT_CC_MODE (GET_CODE (operands[0]),
14895 operands[1], operands[2]) == CCFPmode
14896 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14899 (define_insn "*fp_jcc_5_387"
14901 (if_then_else (match_operator 0 "comparison_operator"
14902 [(match_operand 1 "register_operand" "f")
14903 (match_operand 2 "register_operand" "f")])
14904 (label_ref (match_operand 3 "" ""))
14906 (clobber (reg:CCFP FPSR_REG))
14907 (clobber (reg:CCFP FLAGS_REG))
14908 (clobber (match_scratch:HI 4 "=a"))]
14909 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14910 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14911 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14914 (define_insn "*fp_jcc_6_387"
14916 (if_then_else (match_operator 0 "comparison_operator"
14917 [(match_operand 1 "register_operand" "f")
14918 (match_operand 2 "register_operand" "f")])
14920 (label_ref (match_operand 3 "" ""))))
14921 (clobber (reg:CCFP FPSR_REG))
14922 (clobber (reg:CCFP FLAGS_REG))
14923 (clobber (match_scratch:HI 4 "=a"))]
14924 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14925 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14926 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14929 (define_insn "*fp_jcc_7_387"
14931 (if_then_else (match_operator 0 "comparison_operator"
14932 [(match_operand 1 "register_operand" "f")
14933 (match_operand 2 "const0_operand" "")])
14934 (label_ref (match_operand 3 "" ""))
14936 (clobber (reg:CCFP FPSR_REG))
14937 (clobber (reg:CCFP FLAGS_REG))
14938 (clobber (match_scratch:HI 4 "=a"))]
14939 "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14940 && GET_MODE (operands[1]) == GET_MODE (operands[2])
14941 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14942 && SELECT_CC_MODE (GET_CODE (operands[0]),
14943 operands[1], operands[2]) == CCFPmode
14944 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14947 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
14948 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
14949 ;; with a precedence over other operators and is always put in the first
14950 ;; place. Swap condition and operands to match ficom instruction.
14952 (define_insn "*fp_jcc_8<mode>_387"
14954 (if_then_else (match_operator 0 "comparison_operator"
14955 [(match_operator 1 "float_operator"
14956 [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
14957 (match_operand 3 "register_operand" "f,f")])
14958 (label_ref (match_operand 4 "" ""))
14960 (clobber (reg:CCFP FPSR_REG))
14961 (clobber (reg:CCFP FLAGS_REG))
14962 (clobber (match_scratch:HI 5 "=a,a"))]
14963 "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
14964 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
14965 && GET_MODE (operands[1]) == GET_MODE (operands[3])
14966 && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
14967 && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
14968 && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
14973 (if_then_else (match_operator 0 "comparison_operator"
14974 [(match_operand 1 "register_operand" "")
14975 (match_operand 2 "nonimmediate_operand" "")])
14976 (match_operand 3 "" "")
14977 (match_operand 4 "" "")))
14978 (clobber (reg:CCFP FPSR_REG))
14979 (clobber (reg:CCFP FLAGS_REG))]
14983 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
14984 operands[3], operands[4], NULL_RTX, NULL_RTX);
14990 (if_then_else (match_operator 0 "comparison_operator"
14991 [(match_operand 1 "register_operand" "")
14992 (match_operand 2 "general_operand" "")])
14993 (match_operand 3 "" "")
14994 (match_operand 4 "" "")))
14995 (clobber (reg:CCFP FPSR_REG))
14996 (clobber (reg:CCFP FLAGS_REG))
14997 (clobber (match_scratch:HI 5 "=a"))]
15001 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
15002 operands[3], operands[4], operands[5], NULL_RTX);
15008 (if_then_else (match_operator 0 "comparison_operator"
15009 [(match_operator 1 "float_operator"
15010 [(match_operand:X87MODEI12 2 "memory_operand" "")])
15011 (match_operand 3 "register_operand" "")])
15012 (match_operand 4 "" "")
15013 (match_operand 5 "" "")))
15014 (clobber (reg:CCFP FPSR_REG))
15015 (clobber (reg:CCFP FLAGS_REG))
15016 (clobber (match_scratch:HI 6 "=a"))]
15020 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
15021 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
15022 operands[3], operands[7],
15023 operands[4], operands[5], operands[6], NULL_RTX);
15027 ;; %%% Kill this when reload knows how to do it.
15030 (if_then_else (match_operator 0 "comparison_operator"
15031 [(match_operator 1 "float_operator"
15032 [(match_operand:X87MODEI12 2 "register_operand" "")])
15033 (match_operand 3 "register_operand" "")])
15034 (match_operand 4 "" "")
15035 (match_operand 5 "" "")))
15036 (clobber (reg:CCFP FPSR_REG))
15037 (clobber (reg:CCFP FLAGS_REG))
15038 (clobber (match_scratch:HI 6 "=a"))]
15042 operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
15043 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
15044 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
15045 operands[3], operands[7],
15046 operands[4], operands[5], operands[6], operands[2]);
15050 ;; Unconditional and other jump instructions
15052 (define_insn "jump"
15054 (label_ref (match_operand 0 "" "")))]
15057 [(set_attr "type" "ibr")
15058 (set (attr "length")
15059 (if_then_else (and (ge (minus (match_dup 0) (pc))
15061 (lt (minus (match_dup 0) (pc))
15065 (set_attr "modrm" "0")])
15067 (define_expand "indirect_jump"
15068 [(set (pc) (match_operand 0 "nonimmediate_operand" ""))]
15072 (define_insn "*indirect_jump"
15073 [(set (pc) (match_operand:P 0 "nonimmediate_operand" "rm"))]
15076 [(set_attr "type" "ibr")
15077 (set_attr "length_immediate" "0")])
15079 (define_expand "tablejump"
15080 [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" ""))
15081 (use (label_ref (match_operand 1 "" "")))])]
15084 /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
15085 relative. Convert the relative address to an absolute address. */
15089 enum rtx_code code;
15091 /* We can't use @GOTOFF for text labels on VxWorks;
15092 see gotoff_operand. */
15093 if (TARGET_64BIT || TARGET_VXWORKS_RTP)
15097 op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
15099 else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
15103 op1 = pic_offset_table_rtx;
15108 op0 = pic_offset_table_rtx;
15112 operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
15117 (define_insn "*tablejump_1"
15118 [(set (pc) (match_operand:P 0 "nonimmediate_operand" "rm"))
15119 (use (label_ref (match_operand 1 "" "")))]
15122 [(set_attr "type" "ibr")
15123 (set_attr "length_immediate" "0")])
15125 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
15128 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
15129 (set (match_operand:QI 1 "register_operand" "")
15130 (match_operator:QI 2 "ix86_comparison_operator"
15131 [(reg FLAGS_REG) (const_int 0)]))
15132 (set (match_operand 3 "q_regs_operand" "")
15133 (zero_extend (match_dup 1)))]
15134 "(peep2_reg_dead_p (3, operands[1])
15135 || operands_match_p (operands[1], operands[3]))
15136 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
15137 [(set (match_dup 4) (match_dup 0))
15138 (set (strict_low_part (match_dup 5))
15141 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
15142 operands[5] = gen_lowpart (QImode, operands[3]);
15143 ix86_expand_clear (operands[3]);
15146 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
15149 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
15150 (set (match_operand:QI 1 "register_operand" "")
15151 (match_operator:QI 2 "ix86_comparison_operator"
15152 [(reg FLAGS_REG) (const_int 0)]))
15153 (parallel [(set (match_operand 3 "q_regs_operand" "")
15154 (zero_extend (match_dup 1)))
15155 (clobber (reg:CC FLAGS_REG))])]
15156 "(peep2_reg_dead_p (3, operands[1])
15157 || operands_match_p (operands[1], operands[3]))
15158 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
15159 [(set (match_dup 4) (match_dup 0))
15160 (set (strict_low_part (match_dup 5))
15163 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
15164 operands[5] = gen_lowpart (QImode, operands[3]);
15165 ix86_expand_clear (operands[3]);
15168 ;; Call instructions.
15170 ;; The predicates normally associated with named expanders are not properly
15171 ;; checked for calls. This is a bug in the generic code, but it isn't that
15172 ;; easy to fix. Ignore it for now and be prepared to fix things up.
15174 ;; Call subroutine returning no value.
15176 (define_expand "call_pop"
15177 [(parallel [(call (match_operand:QI 0 "" "")
15178 (match_operand:SI 1 "" ""))
15179 (set (reg:SI SP_REG)
15180 (plus:SI (reg:SI SP_REG)
15181 (match_operand:SI 3 "" "")))])]
15184 ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
15188 (define_insn "*call_pop_0"
15189 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
15190 (match_operand:SI 1 "" ""))
15191 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
15192 (match_operand:SI 2 "immediate_operand" "")))]
15195 if (SIBLING_CALL_P (insn))
15198 return "call\t%P0";
15200 [(set_attr "type" "call")])
15202 (define_insn "*call_pop_1"
15203 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
15204 (match_operand:SI 1 "" ""))
15205 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
15206 (match_operand:SI 2 "immediate_operand" "i")))]
15209 if (constant_call_address_operand (operands[0], Pmode))
15211 if (SIBLING_CALL_P (insn))
15214 return "call\t%P0";
15216 if (SIBLING_CALL_P (insn))
15219 return "call\t%A0";
15221 [(set_attr "type" "call")])
15223 (define_expand "call"
15224 [(call (match_operand:QI 0 "" "")
15225 (match_operand 1 "" ""))
15226 (use (match_operand 2 "" ""))]
15229 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
15233 (define_expand "sibcall"
15234 [(call (match_operand:QI 0 "" "")
15235 (match_operand 1 "" ""))
15236 (use (match_operand 2 "" ""))]
15239 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
15243 (define_insn "*call_0"
15244 [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
15245 (match_operand 1 "" ""))]
15248 if (SIBLING_CALL_P (insn))
15251 return "call\t%P0";
15253 [(set_attr "type" "call")])
15255 (define_insn "*call_1"
15256 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
15257 (match_operand 1 "" ""))]
15258 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
15260 if (constant_call_address_operand (operands[0], Pmode))
15261 return "call\t%P0";
15262 return "call\t%A0";
15264 [(set_attr "type" "call")])
15266 (define_insn "*sibcall_1"
15267 [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
15268 (match_operand 1 "" ""))]
15269 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
15271 if (constant_call_address_operand (operands[0], Pmode))
15275 [(set_attr "type" "call")])
15277 (define_insn "*call_1_rex64"
15278 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
15279 (match_operand 1 "" ""))]
15280 "!SIBLING_CALL_P (insn) && TARGET_64BIT
15281 && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
15283 if (constant_call_address_operand (operands[0], Pmode))
15284 return "call\t%P0";
15285 return "call\t%A0";
15287 [(set_attr "type" "call")])
15289 (define_insn "*call_1_rex64_ms_sysv"
15290 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
15291 (match_operand 1 "" ""))
15292 (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
15293 (clobber (reg:TI XMM6_REG))
15294 (clobber (reg:TI XMM7_REG))
15295 (clobber (reg:TI XMM8_REG))
15296 (clobber (reg:TI XMM9_REG))
15297 (clobber (reg:TI XMM10_REG))
15298 (clobber (reg:TI XMM11_REG))
15299 (clobber (reg:TI XMM12_REG))
15300 (clobber (reg:TI XMM13_REG))
15301 (clobber (reg:TI XMM14_REG))
15302 (clobber (reg:TI XMM15_REG))
15303 (clobber (reg:DI SI_REG))
15304 (clobber (reg:DI DI_REG))]
15305 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
15307 if (constant_call_address_operand (operands[0], Pmode))
15308 return "call\t%P0";
15309 return "call\t%A0";
15311 [(set_attr "type" "call")])
15313 (define_insn "*call_1_rex64_large"
15314 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rm"))
15315 (match_operand 1 "" ""))]
15316 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
15318 [(set_attr "type" "call")])
15320 (define_insn "*sibcall_1_rex64"
15321 [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
15322 (match_operand 1 "" ""))]
15323 "SIBLING_CALL_P (insn) && TARGET_64BIT"
15325 [(set_attr "type" "call")])
15327 (define_insn "*sibcall_1_rex64_v"
15328 [(call (mem:QI (reg:DI R11_REG))
15329 (match_operand 0 "" ""))]
15330 "SIBLING_CALL_P (insn) && TARGET_64BIT"
15332 [(set_attr "type" "call")])
15335 ;; Call subroutine, returning value in operand 0
15337 (define_expand "call_value_pop"
15338 [(parallel [(set (match_operand 0 "" "")
15339 (call (match_operand:QI 1 "" "")
15340 (match_operand:SI 2 "" "")))
15341 (set (reg:SI SP_REG)
15342 (plus:SI (reg:SI SP_REG)
15343 (match_operand:SI 4 "" "")))])]
15346 ix86_expand_call (operands[0], operands[1], operands[2],
15347 operands[3], operands[4], 0);
15351 (define_expand "call_value"
15352 [(set (match_operand 0 "" "")
15353 (call (match_operand:QI 1 "" "")
15354 (match_operand:SI 2 "" "")))
15355 (use (match_operand:SI 3 "" ""))]
15356 ;; Operand 2 not used on the i386.
15359 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
15363 (define_expand "sibcall_value"
15364 [(set (match_operand 0 "" "")
15365 (call (match_operand:QI 1 "" "")
15366 (match_operand:SI 2 "" "")))
15367 (use (match_operand:SI 3 "" ""))]
15368 ;; Operand 2 not used on the i386.
15371 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
15375 ;; Call subroutine returning any type.
15377 (define_expand "untyped_call"
15378 [(parallel [(call (match_operand 0 "" "")
15380 (match_operand 1 "" "")
15381 (match_operand 2 "" "")])]
15386 /* In order to give reg-stack an easier job in validating two
15387 coprocessor registers as containing a possible return value,
15388 simply pretend the untyped call returns a complex long double
15391 We can't use SSE_REGPARM_MAX here since callee is unprototyped
15392 and should have the default ABI. */
15394 ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
15395 ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
15396 operands[0], const0_rtx,
15397 GEN_INT ((TARGET_64BIT
15398 ? (ix86_abi == SYSV_ABI
15399 ? X86_64_SSE_REGPARM_MAX
15400 : X64_SSE_REGPARM_MAX)
15401 : X86_32_SSE_REGPARM_MAX)
15405 for (i = 0; i < XVECLEN (operands[2], 0); i++)
15407 rtx set = XVECEXP (operands[2], 0, i);
15408 emit_move_insn (SET_DEST (set), SET_SRC (set));
15411 /* The optimizer does not know that the call sets the function value
15412 registers we stored in the result block. We avoid problems by
15413 claiming that all hard registers are used and clobbered at this
15415 emit_insn (gen_blockage ());
15420 ;; Prologue and epilogue instructions
15422 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
15423 ;; all of memory. This blocks insns from being moved across this point.
15425 (define_insn "blockage"
15426 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
15429 [(set_attr "length" "0")])
15431 ;; Do not schedule instructions accessing memory across this point.
15433 (define_expand "memory_blockage"
15434 [(set (match_dup 0)
15435 (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
15438 operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
15439 MEM_VOLATILE_P (operands[0]) = 1;
15442 (define_insn "*memory_blockage"
15443 [(set (match_operand:BLK 0 "" "")
15444 (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
15447 [(set_attr "length" "0")])
15449 ;; As USE insns aren't meaningful after reload, this is used instead
15450 ;; to prevent deleting instructions setting registers for PIC code
15451 (define_insn "prologue_use"
15452 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
15455 [(set_attr "length" "0")])
15457 ;; Insn emitted into the body of a function to return from a function.
15458 ;; This is only done if the function's epilogue is known to be simple.
15459 ;; See comments for ix86_can_use_return_insn_p in i386.c.
15461 (define_expand "return"
15463 "ix86_can_use_return_insn_p ()"
15465 if (crtl->args.pops_args)
15467 rtx popc = GEN_INT (crtl->args.pops_args);
15468 emit_jump_insn (gen_return_pop_internal (popc));
15473 (define_insn "return_internal"
15477 [(set_attr "length" "1")
15478 (set_attr "atom_unit" "jeu")
15479 (set_attr "length_immediate" "0")
15480 (set_attr "modrm" "0")])
15482 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
15483 ;; instruction Athlon and K8 have.
15485 (define_insn "return_internal_long"
15487 (unspec [(const_int 0)] UNSPEC_REP)]
15490 [(set_attr "length" "1")
15491 (set_attr "atom_unit" "jeu")
15492 (set_attr "length_immediate" "0")
15493 (set_attr "prefix_rep" "1")
15494 (set_attr "modrm" "0")])
15496 (define_insn "return_pop_internal"
15498 (use (match_operand:SI 0 "const_int_operand" ""))]
15501 [(set_attr "length" "3")
15502 (set_attr "atom_unit" "jeu")
15503 (set_attr "length_immediate" "2")
15504 (set_attr "modrm" "0")])
15506 (define_insn "return_indirect_internal"
15508 (use (match_operand:SI 0 "register_operand" "r"))]
15511 [(set_attr "type" "ibr")
15512 (set_attr "length_immediate" "0")])
15518 [(set_attr "length" "1")
15519 (set_attr "length_immediate" "0")
15520 (set_attr "modrm" "0")])
15522 ;; Pad to 16-byte boundary, max skip in op0. Used to avoid
15523 ;; branch prediction penalty for the third jump in a 16-byte
15527 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
15530 #ifdef ASM_OUTPUT_MAX_SKIP_PAD
15531 ASM_OUTPUT_MAX_SKIP_PAD (asm_out_file, 4, (int)INTVAL (operands[0]));
15533 /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
15534 The align insn is used to avoid 3 jump instructions in the row to improve
15535 branch prediction and the benefits hardly outweigh the cost of extra 8
15536 nops on the average inserted by full alignment pseudo operation. */
15540 [(set_attr "length" "16")])
15542 (define_expand "prologue"
15545 "ix86_expand_prologue (); DONE;")
15547 (define_insn "set_got"
15548 [(set (match_operand:SI 0 "register_operand" "=r")
15549 (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
15550 (clobber (reg:CC FLAGS_REG))]
15552 { return output_set_got (operands[0], NULL_RTX); }
15553 [(set_attr "type" "multi")
15554 (set_attr "length" "12")])
15556 (define_insn "set_got_labelled"
15557 [(set (match_operand:SI 0 "register_operand" "=r")
15558 (unspec:SI [(label_ref (match_operand 1 "" ""))]
15560 (clobber (reg:CC FLAGS_REG))]
15562 { return output_set_got (operands[0], operands[1]); }
15563 [(set_attr "type" "multi")
15564 (set_attr "length" "12")])
15566 (define_insn "set_got_rex64"
15567 [(set (match_operand:DI 0 "register_operand" "=r")
15568 (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
15570 "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
15571 [(set_attr "type" "lea")
15572 (set_attr "length" "6")])
15574 (define_insn "set_rip_rex64"
15575 [(set (match_operand:DI 0 "register_operand" "=r")
15576 (unspec:DI [(label_ref (match_operand 1 "" ""))] UNSPEC_SET_RIP))]
15578 "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
15579 [(set_attr "type" "lea")
15580 (set_attr "length" "6")])
15582 (define_insn "set_got_offset_rex64"
15583 [(set (match_operand:DI 0 "register_operand" "=r")
15585 [(label_ref (match_operand 1 "" ""))]
15586 UNSPEC_SET_GOT_OFFSET))]
15588 "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
15589 [(set_attr "type" "imov")
15590 (set_attr "length" "11")])
15592 (define_expand "epilogue"
15595 "ix86_expand_epilogue (1); DONE;")
15597 (define_expand "sibcall_epilogue"
15600 "ix86_expand_epilogue (0); DONE;")
15602 (define_expand "eh_return"
15603 [(use (match_operand 0 "register_operand" ""))]
15606 rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
15608 /* Tricky bit: we write the address of the handler to which we will
15609 be returning into someone else's stack frame, one word below the
15610 stack address we wish to restore. */
15611 tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
15612 tmp = plus_constant (tmp, -UNITS_PER_WORD);
15613 tmp = gen_rtx_MEM (Pmode, tmp);
15614 emit_move_insn (tmp, ra);
15616 if (Pmode == SImode)
15617 emit_jump_insn (gen_eh_return_si (sa));
15619 emit_jump_insn (gen_eh_return_di (sa));
15624 (define_insn_and_split "eh_return_<mode>"
15626 (unspec [(match_operand:P 0 "register_operand" "c")]
15627 UNSPEC_EH_RETURN))]
15632 "ix86_expand_epilogue (2); DONE;")
15634 (define_insn "leave"
15635 [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
15636 (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
15637 (clobber (mem:BLK (scratch)))]
15640 [(set_attr "type" "leave")])
15642 (define_insn "leave_rex64"
15643 [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
15644 (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
15645 (clobber (mem:BLK (scratch)))]
15648 [(set_attr "type" "leave")])
15650 (define_expand "ffssi2"
15652 [(set (match_operand:SI 0 "register_operand" "")
15653 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15654 (clobber (match_scratch:SI 2 ""))
15655 (clobber (reg:CC FLAGS_REG))])]
15660 emit_insn (gen_ffs_cmove (operands[0], operands[1]));
15665 (define_expand "ffs_cmove"
15666 [(set (match_dup 2) (const_int -1))
15667 (parallel [(set (reg:CCZ FLAGS_REG)
15668 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "")
15670 (set (match_operand:SI 0 "register_operand" "")
15671 (ctz:SI (match_dup 1)))])
15672 (set (match_dup 0) (if_then_else:SI
15673 (eq (reg:CCZ FLAGS_REG) (const_int 0))
15676 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15677 (clobber (reg:CC FLAGS_REG))])]
15679 "operands[2] = gen_reg_rtx (SImode);")
15681 (define_insn_and_split "*ffs_no_cmove"
15682 [(set (match_operand:SI 0 "register_operand" "=r")
15683 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15684 (clobber (match_scratch:SI 2 "=&q"))
15685 (clobber (reg:CC FLAGS_REG))]
15688 "&& reload_completed"
15689 [(parallel [(set (reg:CCZ FLAGS_REG)
15690 (compare:CCZ (match_dup 1) (const_int 0)))
15691 (set (match_dup 0) (ctz:SI (match_dup 1)))])
15692 (set (strict_low_part (match_dup 3))
15693 (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
15694 (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
15695 (clobber (reg:CC FLAGS_REG))])
15696 (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
15697 (clobber (reg:CC FLAGS_REG))])
15698 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15699 (clobber (reg:CC FLAGS_REG))])]
15701 operands[3] = gen_lowpart (QImode, operands[2]);
15702 ix86_expand_clear (operands[2]);
15705 (define_insn "*ffssi_1"
15706 [(set (reg:CCZ FLAGS_REG)
15707 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
15709 (set (match_operand:SI 0 "register_operand" "=r")
15710 (ctz:SI (match_dup 1)))]
15712 "bsf{l}\t{%1, %0|%0, %1}"
15713 [(set_attr "prefix_0f" "1")])
15715 (define_expand "ffsdi2"
15716 [(set (match_dup 2) (const_int -1))
15717 (parallel [(set (reg:CCZ FLAGS_REG)
15718 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "")
15720 (set (match_operand:DI 0 "register_operand" "")
15721 (ctz:DI (match_dup 1)))])
15722 (set (match_dup 0) (if_then_else:DI
15723 (eq (reg:CCZ FLAGS_REG) (const_int 0))
15726 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
15727 (clobber (reg:CC FLAGS_REG))])]
15729 "operands[2] = gen_reg_rtx (DImode);")
15731 (define_insn "*ffsdi_1"
15732 [(set (reg:CCZ FLAGS_REG)
15733 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
15735 (set (match_operand:DI 0 "register_operand" "=r")
15736 (ctz:DI (match_dup 1)))]
15738 "bsf{q}\t{%1, %0|%0, %1}"
15739 [(set_attr "prefix_0f" "1")])
15741 (define_insn "ctzsi2"
15742 [(set (match_operand:SI 0 "register_operand" "=r")
15743 (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15744 (clobber (reg:CC FLAGS_REG))]
15746 "bsf{l}\t{%1, %0|%0, %1}"
15747 [(set_attr "prefix_0f" "1")])
15749 (define_insn "ctzdi2"
15750 [(set (match_operand:DI 0 "register_operand" "=r")
15751 (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
15752 (clobber (reg:CC FLAGS_REG))]
15754 "bsf{q}\t{%1, %0|%0, %1}"
15755 [(set_attr "prefix_0f" "1")])
15757 (define_expand "clzsi2"
15759 [(set (match_operand:SI 0 "register_operand" "")
15760 (minus:SI (const_int 31)
15761 (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
15762 (clobber (reg:CC FLAGS_REG))])
15764 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
15765 (clobber (reg:CC FLAGS_REG))])]
15770 emit_insn (gen_clzsi2_abm (operands[0], operands[1]));
15775 (define_insn "clzsi2_abm"
15776 [(set (match_operand:SI 0 "register_operand" "=r")
15777 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15778 (clobber (reg:CC FLAGS_REG))]
15780 "lzcnt{l}\t{%1, %0|%0, %1}"
15781 [(set_attr "prefix_rep" "1")
15782 (set_attr "type" "bitmanip")
15783 (set_attr "mode" "SI")])
15785 (define_insn "*bsr"
15786 [(set (match_operand:SI 0 "register_operand" "=r")
15787 (minus:SI (const_int 31)
15788 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
15789 (clobber (reg:CC FLAGS_REG))]
15791 "bsr{l}\t{%1, %0|%0, %1}"
15792 [(set_attr "prefix_0f" "1")
15793 (set_attr "mode" "SI")])
15795 (define_insn "popcount<mode>2"
15796 [(set (match_operand:SWI248 0 "register_operand" "=r")
15798 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
15799 (clobber (reg:CC FLAGS_REG))]
15803 return "popcnt\t{%1, %0|%0, %1}";
15805 return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
15808 [(set_attr "prefix_rep" "1")
15809 (set_attr "type" "bitmanip")
15810 (set_attr "mode" "<MODE>")])
15812 (define_insn "*popcount<mode>2_cmp"
15813 [(set (reg FLAGS_REG)
15816 (match_operand:SWI248 1 "nonimmediate_operand" "rm"))
15818 (set (match_operand:SWI248 0 "register_operand" "=r")
15819 (popcount:SWI248 (match_dup 1)))]
15820 "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15823 return "popcnt\t{%1, %0|%0, %1}";
15825 return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
15828 [(set_attr "prefix_rep" "1")
15829 (set_attr "type" "bitmanip")
15830 (set_attr "mode" "<MODE>")])
15832 (define_insn "*popcountsi2_cmp_zext"
15833 [(set (reg FLAGS_REG)
15835 (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
15837 (set (match_operand:DI 0 "register_operand" "=r")
15838 (zero_extend:DI(popcount:SI (match_dup 1))))]
15839 "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15842 return "popcnt\t{%1, %0|%0, %1}";
15844 return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
15847 [(set_attr "prefix_rep" "1")
15848 (set_attr "type" "bitmanip")
15849 (set_attr "mode" "SI")])
15851 (define_expand "bswapsi2"
15852 [(set (match_operand:SI 0 "register_operand" "")
15853 (bswap:SI (match_operand:SI 1 "register_operand" "")))]
15858 rtx x = operands[0];
15860 emit_move_insn (x, operands[1]);
15861 emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15862 emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
15863 emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15868 (define_insn "*bswapsi_1"
15869 [(set (match_operand:SI 0 "register_operand" "=r")
15870 (bswap:SI (match_operand:SI 1 "register_operand" "0")))]
15873 [(set_attr "prefix_0f" "1")
15874 (set_attr "length" "2")])
15876 (define_insn "*bswaphi_lowpart_1"
15877 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
15878 (bswap:HI (match_dup 0)))
15879 (clobber (reg:CC FLAGS_REG))]
15880 "TARGET_USE_XCHGB || optimize_function_for_size_p (cfun)"
15882 xchg{b}\t{%h0, %b0|%b0, %h0}
15883 rol{w}\t{$8, %0|%0, 8}"
15884 [(set_attr "length" "2,4")
15885 (set_attr "mode" "QI,HI")])
15887 (define_insn "bswaphi_lowpart"
15888 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
15889 (bswap:HI (match_dup 0)))
15890 (clobber (reg:CC FLAGS_REG))]
15892 "rol{w}\t{$8, %0|%0, 8}"
15893 [(set_attr "length" "4")
15894 (set_attr "mode" "HI")])
15896 (define_insn "bswapdi2"
15897 [(set (match_operand:DI 0 "register_operand" "=r")
15898 (bswap:DI (match_operand:DI 1 "register_operand" "0")))]
15901 [(set_attr "prefix_0f" "1")
15902 (set_attr "length" "3")])
15904 (define_expand "clzdi2"
15906 [(set (match_operand:DI 0 "register_operand" "")
15907 (minus:DI (const_int 63)
15908 (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
15909 (clobber (reg:CC FLAGS_REG))])
15911 [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
15912 (clobber (reg:CC FLAGS_REG))])]
15917 emit_insn (gen_clzdi2_abm (operands[0], operands[1]));
15922 (define_insn "clzdi2_abm"
15923 [(set (match_operand:DI 0 "register_operand" "=r")
15924 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
15925 (clobber (reg:CC FLAGS_REG))]
15926 "TARGET_64BIT && TARGET_ABM"
15927 "lzcnt{q}\t{%1, %0|%0, %1}"
15928 [(set_attr "prefix_rep" "1")
15929 (set_attr "type" "bitmanip")
15930 (set_attr "mode" "DI")])
15932 (define_insn "*bsr_rex64"
15933 [(set (match_operand:DI 0 "register_operand" "=r")
15934 (minus:DI (const_int 63)
15935 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
15936 (clobber (reg:CC FLAGS_REG))]
15938 "bsr{q}\t{%1, %0|%0, %1}"
15939 [(set_attr "prefix_0f" "1")
15940 (set_attr "mode" "DI")])
15942 (define_expand "clzhi2"
15944 [(set (match_operand:HI 0 "register_operand" "")
15945 (minus:HI (const_int 15)
15946 (clz:HI (match_operand:HI 1 "nonimmediate_operand" ""))))
15947 (clobber (reg:CC FLAGS_REG))])
15949 [(set (match_dup 0) (xor:HI (match_dup 0) (const_int 15)))
15950 (clobber (reg:CC FLAGS_REG))])]
15955 emit_insn (gen_clzhi2_abm (operands[0], operands[1]));
15960 (define_insn "clzhi2_abm"
15961 [(set (match_operand:HI 0 "register_operand" "=r")
15962 (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm")))
15963 (clobber (reg:CC FLAGS_REG))]
15965 "lzcnt{w}\t{%1, %0|%0, %1}"
15966 [(set_attr "prefix_rep" "1")
15967 (set_attr "type" "bitmanip")
15968 (set_attr "mode" "HI")])
15970 (define_insn "*bsrhi"
15971 [(set (match_operand:HI 0 "register_operand" "=r")
15972 (minus:HI (const_int 15)
15973 (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
15974 (clobber (reg:CC FLAGS_REG))]
15976 "bsr{w}\t{%1, %0|%0, %1}"
15977 [(set_attr "prefix_0f" "1")
15978 (set_attr "mode" "HI")])
15980 (define_expand "paritydi2"
15981 [(set (match_operand:DI 0 "register_operand" "")
15982 (parity:DI (match_operand:DI 1 "register_operand" "")))]
15985 rtx scratch = gen_reg_rtx (QImode);
15988 emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
15989 NULL_RTX, operands[1]));
15991 cond = gen_rtx_fmt_ee (ORDERED, QImode,
15992 gen_rtx_REG (CCmode, FLAGS_REG),
15994 emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
15997 emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
16000 rtx tmp = gen_reg_rtx (SImode);
16002 emit_insn (gen_zero_extendqisi2 (tmp, scratch));
16003 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
16008 (define_insn_and_split "paritydi2_cmp"
16009 [(set (reg:CC FLAGS_REG)
16010 (parity:CC (match_operand:DI 3 "register_operand" "0")))
16011 (clobber (match_scratch:DI 0 "=r"))
16012 (clobber (match_scratch:SI 1 "=&r"))
16013 (clobber (match_scratch:HI 2 "=Q"))]
16016 "&& reload_completed"
16018 [(set (match_dup 1)
16019 (xor:SI (match_dup 1) (match_dup 4)))
16020 (clobber (reg:CC FLAGS_REG))])
16022 [(set (reg:CC FLAGS_REG)
16023 (parity:CC (match_dup 1)))
16024 (clobber (match_dup 1))
16025 (clobber (match_dup 2))])]
16027 operands[4] = gen_lowpart (SImode, operands[3]);
16031 emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
16032 emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
16035 operands[1] = gen_highpart (SImode, operands[3]);
16038 (define_expand "paritysi2"
16039 [(set (match_operand:SI 0 "register_operand" "")
16040 (parity:SI (match_operand:SI 1 "register_operand" "")))]
16043 rtx scratch = gen_reg_rtx (QImode);
16046 emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
16048 cond = gen_rtx_fmt_ee (ORDERED, QImode,
16049 gen_rtx_REG (CCmode, FLAGS_REG),
16051 emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
16053 emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
16057 (define_insn_and_split "paritysi2_cmp"
16058 [(set (reg:CC FLAGS_REG)
16059 (parity:CC (match_operand:SI 2 "register_operand" "0")))
16060 (clobber (match_scratch:SI 0 "=r"))
16061 (clobber (match_scratch:HI 1 "=&Q"))]
16064 "&& reload_completed"
16066 [(set (match_dup 1)
16067 (xor:HI (match_dup 1) (match_dup 3)))
16068 (clobber (reg:CC FLAGS_REG))])
16070 [(set (reg:CC FLAGS_REG)
16071 (parity:CC (match_dup 1)))
16072 (clobber (match_dup 1))])]
16074 operands[3] = gen_lowpart (HImode, operands[2]);
16076 emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
16077 emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
16080 (define_insn "*parityhi2_cmp"
16081 [(set (reg:CC FLAGS_REG)
16082 (parity:CC (match_operand:HI 1 "register_operand" "0")))
16083 (clobber (match_scratch:HI 0 "=Q"))]
16085 "xor{b}\t{%h0, %b0|%b0, %h0}"
16086 [(set_attr "length" "2")
16087 (set_attr "mode" "HI")])
16089 (define_insn "*parityqi2_cmp"
16090 [(set (reg:CC FLAGS_REG)
16091 (parity:CC (match_operand:QI 0 "register_operand" "q")))]
16094 [(set_attr "length" "2")
16095 (set_attr "mode" "QI")])
16097 ;; Thread-local storage patterns for ELF.
16099 ;; Note that these code sequences must appear exactly as shown
16100 ;; in order to allow linker relaxation.
16102 (define_insn "*tls_global_dynamic_32_gnu"
16103 [(set (match_operand:SI 0 "register_operand" "=a")
16104 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
16105 (match_operand:SI 2 "tls_symbolic_operand" "")
16106 (match_operand:SI 3 "call_insn_operand" "")]
16108 (clobber (match_scratch:SI 4 "=d"))
16109 (clobber (match_scratch:SI 5 "=c"))
16110 (clobber (reg:CC FLAGS_REG))]
16111 "!TARGET_64BIT && TARGET_GNU_TLS"
16112 "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
16113 [(set_attr "type" "multi")
16114 (set_attr "length" "12")])
16116 (define_insn "*tls_global_dynamic_32_sun"
16117 [(set (match_operand:SI 0 "register_operand" "=a")
16118 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
16119 (match_operand:SI 2 "tls_symbolic_operand" "")
16120 (match_operand:SI 3 "call_insn_operand" "")]
16122 (clobber (match_scratch:SI 4 "=d"))
16123 (clobber (match_scratch:SI 5 "=c"))
16124 (clobber (reg:CC FLAGS_REG))]
16125 "!TARGET_64BIT && TARGET_SUN_TLS"
16126 "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
16127 push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
16128 [(set_attr "type" "multi")
16129 (set_attr "length" "14")])
16131 (define_expand "tls_global_dynamic_32"
16132 [(parallel [(set (match_operand:SI 0 "register_operand" "")
16135 (match_operand:SI 1 "tls_symbolic_operand" "")
16138 (clobber (match_scratch:SI 4 ""))
16139 (clobber (match_scratch:SI 5 ""))
16140 (clobber (reg:CC FLAGS_REG))])]
16144 operands[2] = pic_offset_table_rtx;
16147 operands[2] = gen_reg_rtx (Pmode);
16148 emit_insn (gen_set_got (operands[2]));
16150 if (TARGET_GNU2_TLS)
16152 emit_insn (gen_tls_dynamic_gnu2_32
16153 (operands[0], operands[1], operands[2]));
16156 operands[3] = ix86_tls_get_addr ();
16159 (define_insn "*tls_global_dynamic_64"
16160 [(set (match_operand:DI 0 "register_operand" "=a")
16161 (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
16162 (match_operand:DI 3 "" "")))
16163 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
16166 ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|rdi, %a1@TLSGD[rip]}\;.word\t0x6666\;rex64\;call\t%P2"
16167 [(set_attr "type" "multi")
16168 (set_attr "length" "16")])
16170 (define_expand "tls_global_dynamic_64"
16171 [(parallel [(set (match_operand:DI 0 "register_operand" "")
16172 (call:DI (mem:QI (match_dup 2)) (const_int 0)))
16173 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
16177 if (TARGET_GNU2_TLS)
16179 emit_insn (gen_tls_dynamic_gnu2_64
16180 (operands[0], operands[1]));
16183 operands[2] = ix86_tls_get_addr ();
16186 (define_insn "*tls_local_dynamic_base_32_gnu"
16187 [(set (match_operand:SI 0 "register_operand" "=a")
16188 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
16189 (match_operand:SI 2 "call_insn_operand" "")]
16190 UNSPEC_TLS_LD_BASE))
16191 (clobber (match_scratch:SI 3 "=d"))
16192 (clobber (match_scratch:SI 4 "=c"))
16193 (clobber (reg:CC FLAGS_REG))]
16194 "!TARGET_64BIT && TARGET_GNU_TLS"
16195 "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
16196 [(set_attr "type" "multi")
16197 (set_attr "length" "11")])
16199 (define_insn "*tls_local_dynamic_base_32_sun"
16200 [(set (match_operand:SI 0 "register_operand" "=a")
16201 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
16202 (match_operand:SI 2 "call_insn_operand" "")]
16203 UNSPEC_TLS_LD_BASE))
16204 (clobber (match_scratch:SI 3 "=d"))
16205 (clobber (match_scratch:SI 4 "=c"))
16206 (clobber (reg:CC FLAGS_REG))]
16207 "!TARGET_64BIT && TARGET_SUN_TLS"
16208 "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
16209 push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
16210 [(set_attr "type" "multi")
16211 (set_attr "length" "13")])
16213 (define_expand "tls_local_dynamic_base_32"
16214 [(parallel [(set (match_operand:SI 0 "register_operand" "")
16215 (unspec:SI [(match_dup 1) (match_dup 2)]
16216 UNSPEC_TLS_LD_BASE))
16217 (clobber (match_scratch:SI 3 ""))
16218 (clobber (match_scratch:SI 4 ""))
16219 (clobber (reg:CC FLAGS_REG))])]
16223 operands[1] = pic_offset_table_rtx;
16226 operands[1] = gen_reg_rtx (Pmode);
16227 emit_insn (gen_set_got (operands[1]));
16229 if (TARGET_GNU2_TLS)
16231 emit_insn (gen_tls_dynamic_gnu2_32
16232 (operands[0], ix86_tls_module_base (), operands[1]));
16235 operands[2] = ix86_tls_get_addr ();
16238 (define_insn "*tls_local_dynamic_base_64"
16239 [(set (match_operand:DI 0 "register_operand" "=a")
16240 (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
16241 (match_operand:DI 2 "" "")))
16242 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
16244 "lea{q}\t{%&@TLSLD(%%rip), %%rdi|rdi, %&@TLSLD[rip]}\;call\t%P1"
16245 [(set_attr "type" "multi")
16246 (set_attr "length" "12")])
16248 (define_expand "tls_local_dynamic_base_64"
16249 [(parallel [(set (match_operand:DI 0 "register_operand" "")
16250 (call:DI (mem:QI (match_dup 1)) (const_int 0)))
16251 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
16254 if (TARGET_GNU2_TLS)
16256 emit_insn (gen_tls_dynamic_gnu2_64
16257 (operands[0], ix86_tls_module_base ()));
16260 operands[1] = ix86_tls_get_addr ();
16263 ;; Local dynamic of a single variable is a lose. Show combine how
16264 ;; to convert that back to global dynamic.
16266 (define_insn_and_split "*tls_local_dynamic_32_once"
16267 [(set (match_operand:SI 0 "register_operand" "=a")
16268 (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
16269 (match_operand:SI 2 "call_insn_operand" "")]
16270 UNSPEC_TLS_LD_BASE)
16271 (const:SI (unspec:SI
16272 [(match_operand:SI 3 "tls_symbolic_operand" "")]
16274 (clobber (match_scratch:SI 4 "=d"))
16275 (clobber (match_scratch:SI 5 "=c"))
16276 (clobber (reg:CC FLAGS_REG))]
16280 [(parallel [(set (match_dup 0)
16281 (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
16283 (clobber (match_dup 4))
16284 (clobber (match_dup 5))
16285 (clobber (reg:CC FLAGS_REG))])]
16288 ;; Load and add the thread base pointer from %gs:0.
16290 (define_insn "*load_tp_si"
16291 [(set (match_operand:SI 0 "register_operand" "=r")
16292 (unspec:SI [(const_int 0)] UNSPEC_TP))]
16294 "mov{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
16295 [(set_attr "type" "imov")
16296 (set_attr "modrm" "0")
16297 (set_attr "length" "7")
16298 (set_attr "memory" "load")
16299 (set_attr "imm_disp" "false")])
16301 (define_insn "*add_tp_si"
16302 [(set (match_operand:SI 0 "register_operand" "=r")
16303 (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
16304 (match_operand:SI 1 "register_operand" "0")))
16305 (clobber (reg:CC FLAGS_REG))]
16307 "add{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
16308 [(set_attr "type" "alu")
16309 (set_attr "modrm" "0")
16310 (set_attr "length" "7")
16311 (set_attr "memory" "load")
16312 (set_attr "imm_disp" "false")])
16314 (define_insn "*load_tp_di"
16315 [(set (match_operand:DI 0 "register_operand" "=r")
16316 (unspec:DI [(const_int 0)] UNSPEC_TP))]
16318 "mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
16319 [(set_attr "type" "imov")
16320 (set_attr "modrm" "0")
16321 (set_attr "length" "7")
16322 (set_attr "memory" "load")
16323 (set_attr "imm_disp" "false")])
16325 (define_insn "*add_tp_di"
16326 [(set (match_operand:DI 0 "register_operand" "=r")
16327 (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
16328 (match_operand:DI 1 "register_operand" "0")))
16329 (clobber (reg:CC FLAGS_REG))]
16331 "add{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
16332 [(set_attr "type" "alu")
16333 (set_attr "modrm" "0")
16334 (set_attr "length" "7")
16335 (set_attr "memory" "load")
16336 (set_attr "imm_disp" "false")])
16338 ;; GNU2 TLS patterns can be split.
16340 (define_expand "tls_dynamic_gnu2_32"
16341 [(set (match_dup 3)
16342 (plus:SI (match_operand:SI 2 "register_operand" "")
16344 (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
16347 [(set (match_operand:SI 0 "register_operand" "")
16348 (unspec:SI [(match_dup 1) (match_dup 3)
16349 (match_dup 2) (reg:SI SP_REG)]
16351 (clobber (reg:CC FLAGS_REG))])]
16352 "!TARGET_64BIT && TARGET_GNU2_TLS"
16354 operands[3] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
16355 ix86_tls_descriptor_calls_expanded_in_cfun = true;
16358 (define_insn "*tls_dynamic_lea_32"
16359 [(set (match_operand:SI 0 "register_operand" "=r")
16360 (plus:SI (match_operand:SI 1 "register_operand" "b")
16362 (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
16363 UNSPEC_TLSDESC))))]
16364 "!TARGET_64BIT && TARGET_GNU2_TLS"
16365 "lea{l}\t{%a2@TLSDESC(%1), %0|%0, %a2@TLSDESC[%1]}"
16366 [(set_attr "type" "lea")
16367 (set_attr "mode" "SI")
16368 (set_attr "length" "6")
16369 (set_attr "length_address" "4")])
16371 (define_insn "*tls_dynamic_call_32"
16372 [(set (match_operand:SI 0 "register_operand" "=a")
16373 (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
16374 (match_operand:SI 2 "register_operand" "0")
16375 ;; we have to make sure %ebx still points to the GOT
16376 (match_operand:SI 3 "register_operand" "b")
16379 (clobber (reg:CC FLAGS_REG))]
16380 "!TARGET_64BIT && TARGET_GNU2_TLS"
16381 "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
16382 [(set_attr "type" "call")
16383 (set_attr "length" "2")
16384 (set_attr "length_address" "0")])
16386 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
16387 [(set (match_operand:SI 0 "register_operand" "=&a")
16389 (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
16390 (match_operand:SI 4 "" "")
16391 (match_operand:SI 2 "register_operand" "b")
16394 (const:SI (unspec:SI
16395 [(match_operand:SI 1 "tls_symbolic_operand" "")]
16397 (clobber (reg:CC FLAGS_REG))]
16398 "!TARGET_64BIT && TARGET_GNU2_TLS"
16401 [(set (match_dup 0) (match_dup 5))]
16403 operands[5] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
16404 emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
16407 (define_expand "tls_dynamic_gnu2_64"
16408 [(set (match_dup 2)
16409 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
16412 [(set (match_operand:DI 0 "register_operand" "")
16413 (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
16415 (clobber (reg:CC FLAGS_REG))])]
16416 "TARGET_64BIT && TARGET_GNU2_TLS"
16418 operands[2] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
16419 ix86_tls_descriptor_calls_expanded_in_cfun = true;
16422 (define_insn "*tls_dynamic_lea_64"
16423 [(set (match_operand:DI 0 "register_operand" "=r")
16424 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
16426 "TARGET_64BIT && TARGET_GNU2_TLS"
16427 "lea{q}\t{%a1@TLSDESC(%%rip), %0|%0, %a1@TLSDESC[rip]}"
16428 [(set_attr "type" "lea")
16429 (set_attr "mode" "DI")
16430 (set_attr "length" "7")
16431 (set_attr "length_address" "4")])
16433 (define_insn "*tls_dynamic_call_64"
16434 [(set (match_operand:DI 0 "register_operand" "=a")
16435 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")
16436 (match_operand:DI 2 "register_operand" "0")
16439 (clobber (reg:CC FLAGS_REG))]
16440 "TARGET_64BIT && TARGET_GNU2_TLS"
16441 "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
16442 [(set_attr "type" "call")
16443 (set_attr "length" "2")
16444 (set_attr "length_address" "0")])
16446 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
16447 [(set (match_operand:DI 0 "register_operand" "=&a")
16449 (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
16450 (match_operand:DI 3 "" "")
16453 (const:DI (unspec:DI
16454 [(match_operand:DI 1 "tls_symbolic_operand" "")]
16456 (clobber (reg:CC FLAGS_REG))]
16457 "TARGET_64BIT && TARGET_GNU2_TLS"
16460 [(set (match_dup 0) (match_dup 4))]
16462 operands[4] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
16463 emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
16468 ;; These patterns match the binary 387 instructions for addM3, subM3,
16469 ;; mulM3 and divM3. There are three patterns for each of DFmode and
16470 ;; SFmode. The first is the normal insn, the second the same insn but
16471 ;; with one operand a conversion, and the third the same insn but with
16472 ;; the other operand a conversion. The conversion may be SFmode or
16473 ;; SImode if the target mode DFmode, but only SImode if the target mode
16476 ;; Gcc is slightly more smart about handling normal two address instructions
16477 ;; so use special patterns for add and mull.
16479 (define_insn "*fop_<mode>_comm_mixed_avx"
16480 [(set (match_operand:MODEF 0 "register_operand" "=f,x")
16481 (match_operator:MODEF 3 "binary_fp_operator"
16482 [(match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
16483 (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm")]))]
16484 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
16485 && COMMUTATIVE_ARITH_P (operands[3])
16486 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16487 "* return output_387_binary_op (insn, operands);"
16488 [(set (attr "type")
16489 (if_then_else (eq_attr "alternative" "1")
16490 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16491 (const_string "ssemul")
16492 (const_string "sseadd"))
16493 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16494 (const_string "fmul")
16495 (const_string "fop"))))
16496 (set_attr "prefix" "orig,maybe_vex")
16497 (set_attr "mode" "<MODE>")])
16499 (define_insn "*fop_<mode>_comm_mixed"
16500 [(set (match_operand:MODEF 0 "register_operand" "=f,x")
16501 (match_operator:MODEF 3 "binary_fp_operator"
16502 [(match_operand:MODEF 1 "nonimmediate_operand" "%0,0")
16503 (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm")]))]
16504 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
16505 && COMMUTATIVE_ARITH_P (operands[3])
16506 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16507 "* return output_387_binary_op (insn, operands);"
16508 [(set (attr "type")
16509 (if_then_else (eq_attr "alternative" "1")
16510 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16511 (const_string "ssemul")
16512 (const_string "sseadd"))
16513 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16514 (const_string "fmul")
16515 (const_string "fop"))))
16516 (set_attr "mode" "<MODE>")])
16518 (define_insn "*fop_<mode>_comm_avx"
16519 [(set (match_operand:MODEF 0 "register_operand" "=x")
16520 (match_operator:MODEF 3 "binary_fp_operator"
16521 [(match_operand:MODEF 1 "nonimmediate_operand" "%x")
16522 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
16523 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16524 && COMMUTATIVE_ARITH_P (operands[3])
16525 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16526 "* return output_387_binary_op (insn, operands);"
16527 [(set (attr "type")
16528 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16529 (const_string "ssemul")
16530 (const_string "sseadd")))
16531 (set_attr "prefix" "vex")
16532 (set_attr "mode" "<MODE>")])
16534 (define_insn "*fop_<mode>_comm_sse"
16535 [(set (match_operand:MODEF 0 "register_operand" "=x")
16536 (match_operator:MODEF 3 "binary_fp_operator"
16537 [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
16538 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
16539 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16540 && COMMUTATIVE_ARITH_P (operands[3])
16541 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16542 "* return output_387_binary_op (insn, operands);"
16543 [(set (attr "type")
16544 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16545 (const_string "ssemul")
16546 (const_string "sseadd")))
16547 (set_attr "mode" "<MODE>")])
16549 (define_insn "*fop_<mode>_comm_i387"
16550 [(set (match_operand:MODEF 0 "register_operand" "=f")
16551 (match_operator:MODEF 3 "binary_fp_operator"
16552 [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
16553 (match_operand:MODEF 2 "nonimmediate_operand" "fm")]))]
16554 "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
16555 && COMMUTATIVE_ARITH_P (operands[3])
16556 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16557 "* return output_387_binary_op (insn, operands);"
16558 [(set (attr "type")
16559 (if_then_else (match_operand:MODEF 3 "mult_operator" "")
16560 (const_string "fmul")
16561 (const_string "fop")))
16562 (set_attr "mode" "<MODE>")])
16564 (define_insn "*fop_<mode>_1_mixed_avx"
16565 [(set (match_operand:MODEF 0 "register_operand" "=f,f,x")
16566 (match_operator:MODEF 3 "binary_fp_operator"
16567 [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,x")
16568 (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm")]))]
16569 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
16570 && !COMMUTATIVE_ARITH_P (operands[3])
16571 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16572 "* return output_387_binary_op (insn, operands);"
16573 [(set (attr "type")
16574 (cond [(and (eq_attr "alternative" "2")
16575 (match_operand:MODEF 3 "mult_operator" ""))
16576 (const_string "ssemul")
16577 (and (eq_attr "alternative" "2")
16578 (match_operand:MODEF 3 "div_operator" ""))
16579 (const_string "ssediv")
16580 (eq_attr "alternative" "2")
16581 (const_string "sseadd")
16582 (match_operand:MODEF 3 "mult_operator" "")
16583 (const_string "fmul")
16584 (match_operand:MODEF 3 "div_operator" "")
16585 (const_string "fdiv")
16587 (const_string "fop")))
16588 (set_attr "prefix" "orig,orig,maybe_vex")
16589 (set_attr "mode" "<MODE>")])
16591 (define_insn "*fop_<mode>_1_mixed"
16592 [(set (match_operand:MODEF 0 "register_operand" "=f,f,x")
16593 (match_operator:MODEF 3 "binary_fp_operator"
16594 [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,0")
16595 (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm")]))]
16596 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
16597 && !COMMUTATIVE_ARITH_P (operands[3])
16598 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16599 "* return output_387_binary_op (insn, operands);"
16600 [(set (attr "type")
16601 (cond [(and (eq_attr "alternative" "2")
16602 (match_operand:MODEF 3 "mult_operator" ""))
16603 (const_string "ssemul")
16604 (and (eq_attr "alternative" "2")
16605 (match_operand:MODEF 3 "div_operator" ""))
16606 (const_string "ssediv")
16607 (eq_attr "alternative" "2")
16608 (const_string "sseadd")
16609 (match_operand:MODEF 3 "mult_operator" "")
16610 (const_string "fmul")
16611 (match_operand:MODEF 3 "div_operator" "")
16612 (const_string "fdiv")
16614 (const_string "fop")))
16615 (set_attr "mode" "<MODE>")])
16617 (define_insn "*rcpsf2_sse"
16618 [(set (match_operand:SF 0 "register_operand" "=x")
16619 (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
16622 "%vrcpss\t{%1, %d0|%d0, %1}"
16623 [(set_attr "type" "sse")
16624 (set_attr "atom_sse_attr" "rcp")
16625 (set_attr "prefix" "maybe_vex")
16626 (set_attr "mode" "SF")])
16628 (define_insn "*fop_<mode>_1_avx"
16629 [(set (match_operand:MODEF 0 "register_operand" "=x")
16630 (match_operator:MODEF 3 "binary_fp_operator"
16631 [(match_operand:MODEF 1 "register_operand" "x")
16632 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
16633 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16634 && !COMMUTATIVE_ARITH_P (operands[3])"
16635 "* return output_387_binary_op (insn, operands);"
16636 [(set (attr "type")
16637 (cond [(match_operand:MODEF 3 "mult_operator" "")
16638 (const_string "ssemul")
16639 (match_operand:MODEF 3 "div_operator" "")
16640 (const_string "ssediv")
16642 (const_string "sseadd")))
16643 (set_attr "prefix" "vex")
16644 (set_attr "mode" "<MODE>")])
16646 (define_insn "*fop_<mode>_1_sse"
16647 [(set (match_operand:MODEF 0 "register_operand" "=x")
16648 (match_operator:MODEF 3 "binary_fp_operator"
16649 [(match_operand:MODEF 1 "register_operand" "0")
16650 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
16651 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16652 && !COMMUTATIVE_ARITH_P (operands[3])"
16653 "* return output_387_binary_op (insn, operands);"
16654 [(set (attr "type")
16655 (cond [(match_operand:MODEF 3 "mult_operator" "")
16656 (const_string "ssemul")
16657 (match_operand:MODEF 3 "div_operator" "")
16658 (const_string "ssediv")
16660 (const_string "sseadd")))
16661 (set_attr "mode" "<MODE>")])
16663 ;; This pattern is not fully shadowed by the pattern above.
16664 (define_insn "*fop_<mode>_1_i387"
16665 [(set (match_operand:MODEF 0 "register_operand" "=f,f")
16666 (match_operator:MODEF 3 "binary_fp_operator"
16667 [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm")
16668 (match_operand:MODEF 2 "nonimmediate_operand" "fm,0")]))]
16669 "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
16670 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16671 && !COMMUTATIVE_ARITH_P (operands[3])
16672 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16673 "* return output_387_binary_op (insn, operands);"
16674 [(set (attr "type")
16675 (cond [(match_operand:MODEF 3 "mult_operator" "")
16676 (const_string "fmul")
16677 (match_operand:MODEF 3 "div_operator" "")
16678 (const_string "fdiv")
16680 (const_string "fop")))
16681 (set_attr "mode" "<MODE>")])
16683 ;; ??? Add SSE splitters for these!
16684 (define_insn "*fop_<MODEF:mode>_2_i387"
16685 [(set (match_operand:MODEF 0 "register_operand" "=f,f")
16686 (match_operator:MODEF 3 "binary_fp_operator"
16688 (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16689 (match_operand:MODEF 2 "register_operand" "0,0")]))]
16690 "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <X87MODEI12:MODE>mode)
16691 && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
16692 && (TARGET_USE_<X87MODEI12:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
16693 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16694 [(set (attr "type")
16695 (cond [(match_operand:MODEF 3 "mult_operator" "")
16696 (const_string "fmul")
16697 (match_operand:MODEF 3 "div_operator" "")
16698 (const_string "fdiv")
16700 (const_string "fop")))
16701 (set_attr "fp_int_src" "true")
16702 (set_attr "mode" "<X87MODEI12:MODE>")])
16704 (define_insn "*fop_<MODEF:mode>_3_i387"
16705 [(set (match_operand:MODEF 0 "register_operand" "=f,f")
16706 (match_operator:MODEF 3 "binary_fp_operator"
16707 [(match_operand:MODEF 1 "register_operand" "0,0")
16709 (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16710 "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <X87MODEI12:MODE>mode)
16711 && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
16712 && (TARGET_USE_<X87MODEI12:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
16713 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16714 [(set (attr "type")
16715 (cond [(match_operand:MODEF 3 "mult_operator" "")
16716 (const_string "fmul")
16717 (match_operand:MODEF 3 "div_operator" "")
16718 (const_string "fdiv")
16720 (const_string "fop")))
16721 (set_attr "fp_int_src" "true")
16722 (set_attr "mode" "<MODE>")])
16724 (define_insn "*fop_df_4_i387"
16725 [(set (match_operand:DF 0 "register_operand" "=f,f")
16726 (match_operator:DF 3 "binary_fp_operator"
16728 (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
16729 (match_operand:DF 2 "register_operand" "0,f")]))]
16730 "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
16731 && !(TARGET_SSE2 && TARGET_SSE_MATH)
16732 && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16733 "* return output_387_binary_op (insn, operands);"
16734 [(set (attr "type")
16735 (cond [(match_operand:DF 3 "mult_operator" "")
16736 (const_string "fmul")
16737 (match_operand:DF 3 "div_operator" "")
16738 (const_string "fdiv")
16740 (const_string "fop")))
16741 (set_attr "mode" "SF")])
16743 (define_insn "*fop_df_5_i387"
16744 [(set (match_operand:DF 0 "register_operand" "=f,f")
16745 (match_operator:DF 3 "binary_fp_operator"
16746 [(match_operand:DF 1 "register_operand" "0,f")
16748 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16749 "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
16750 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16751 "* return output_387_binary_op (insn, operands);"
16752 [(set (attr "type")
16753 (cond [(match_operand:DF 3 "mult_operator" "")
16754 (const_string "fmul")
16755 (match_operand:DF 3 "div_operator" "")
16756 (const_string "fdiv")
16758 (const_string "fop")))
16759 (set_attr "mode" "SF")])
16761 (define_insn "*fop_df_6_i387"
16762 [(set (match_operand:DF 0 "register_operand" "=f,f")
16763 (match_operator:DF 3 "binary_fp_operator"
16765 (match_operand:SF 1 "register_operand" "0,f"))
16767 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16768 "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
16769 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16770 "* return output_387_binary_op (insn, operands);"
16771 [(set (attr "type")
16772 (cond [(match_operand:DF 3 "mult_operator" "")
16773 (const_string "fmul")
16774 (match_operand:DF 3 "div_operator" "")
16775 (const_string "fdiv")
16777 (const_string "fop")))
16778 (set_attr "mode" "SF")])
16780 (define_insn "*fop_xf_comm_i387"
16781 [(set (match_operand:XF 0 "register_operand" "=f")
16782 (match_operator:XF 3 "binary_fp_operator"
16783 [(match_operand:XF 1 "register_operand" "%0")
16784 (match_operand:XF 2 "register_operand" "f")]))]
16786 && COMMUTATIVE_ARITH_P (operands[3])"
16787 "* return output_387_binary_op (insn, operands);"
16788 [(set (attr "type")
16789 (if_then_else (match_operand:XF 3 "mult_operator" "")
16790 (const_string "fmul")
16791 (const_string "fop")))
16792 (set_attr "mode" "XF")])
16794 (define_insn "*fop_xf_1_i387"
16795 [(set (match_operand:XF 0 "register_operand" "=f,f")
16796 (match_operator:XF 3 "binary_fp_operator"
16797 [(match_operand:XF 1 "register_operand" "0,f")
16798 (match_operand:XF 2 "register_operand" "f,0")]))]
16800 && !COMMUTATIVE_ARITH_P (operands[3])"
16801 "* return output_387_binary_op (insn, operands);"
16802 [(set (attr "type")
16803 (cond [(match_operand:XF 3 "mult_operator" "")
16804 (const_string "fmul")
16805 (match_operand:XF 3 "div_operator" "")
16806 (const_string "fdiv")
16808 (const_string "fop")))
16809 (set_attr "mode" "XF")])
16811 (define_insn "*fop_xf_2_i387"
16812 [(set (match_operand:XF 0 "register_operand" "=f,f")
16813 (match_operator:XF 3 "binary_fp_operator"
16815 (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16816 (match_operand:XF 2 "register_operand" "0,0")]))]
16817 "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
16818 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16819 [(set (attr "type")
16820 (cond [(match_operand:XF 3 "mult_operator" "")
16821 (const_string "fmul")
16822 (match_operand:XF 3 "div_operator" "")
16823 (const_string "fdiv")
16825 (const_string "fop")))
16826 (set_attr "fp_int_src" "true")
16827 (set_attr "mode" "<MODE>")])
16829 (define_insn "*fop_xf_3_i387"
16830 [(set (match_operand:XF 0 "register_operand" "=f,f")
16831 (match_operator:XF 3 "binary_fp_operator"
16832 [(match_operand:XF 1 "register_operand" "0,0")
16834 (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16835 "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
16836 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16837 [(set (attr "type")
16838 (cond [(match_operand:XF 3 "mult_operator" "")
16839 (const_string "fmul")
16840 (match_operand:XF 3 "div_operator" "")
16841 (const_string "fdiv")
16843 (const_string "fop")))
16844 (set_attr "fp_int_src" "true")
16845 (set_attr "mode" "<MODE>")])
16847 (define_insn "*fop_xf_4_i387"
16848 [(set (match_operand:XF 0 "register_operand" "=f,f")
16849 (match_operator:XF 3 "binary_fp_operator"
16851 (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
16852 (match_operand:XF 2 "register_operand" "0,f")]))]
16854 "* return output_387_binary_op (insn, operands);"
16855 [(set (attr "type")
16856 (cond [(match_operand:XF 3 "mult_operator" "")
16857 (const_string "fmul")
16858 (match_operand:XF 3 "div_operator" "")
16859 (const_string "fdiv")
16861 (const_string "fop")))
16862 (set_attr "mode" "<MODE>")])
16864 (define_insn "*fop_xf_5_i387"
16865 [(set (match_operand:XF 0 "register_operand" "=f,f")
16866 (match_operator:XF 3 "binary_fp_operator"
16867 [(match_operand:XF 1 "register_operand" "0,f")
16869 (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16871 "* return output_387_binary_op (insn, operands);"
16872 [(set (attr "type")
16873 (cond [(match_operand:XF 3 "mult_operator" "")
16874 (const_string "fmul")
16875 (match_operand:XF 3 "div_operator" "")
16876 (const_string "fdiv")
16878 (const_string "fop")))
16879 (set_attr "mode" "<MODE>")])
16881 (define_insn "*fop_xf_6_i387"
16882 [(set (match_operand:XF 0 "register_operand" "=f,f")
16883 (match_operator:XF 3 "binary_fp_operator"
16885 (match_operand:MODEF 1 "register_operand" "0,f"))
16887 (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16889 "* return output_387_binary_op (insn, operands);"
16890 [(set (attr "type")
16891 (cond [(match_operand:XF 3 "mult_operator" "")
16892 (const_string "fmul")
16893 (match_operand:XF 3 "div_operator" "")
16894 (const_string "fdiv")
16896 (const_string "fop")))
16897 (set_attr "mode" "<MODE>")])
16900 [(set (match_operand 0 "register_operand" "")
16901 (match_operator 3 "binary_fp_operator"
16902 [(float (match_operand:X87MODEI12 1 "register_operand" ""))
16903 (match_operand 2 "register_operand" "")]))]
16905 && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
16906 && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[1]))"
16909 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
16910 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16911 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16912 gen_rtx_fmt_ee (GET_CODE (operands[3]),
16913 GET_MODE (operands[3]),
16916 ix86_free_from_memory (GET_MODE (operands[1]));
16921 [(set (match_operand 0 "register_operand" "")
16922 (match_operator 3 "binary_fp_operator"
16923 [(match_operand 1 "register_operand" "")
16924 (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
16926 && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
16927 && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[2]))"
16930 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
16931 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16932 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16933 gen_rtx_fmt_ee (GET_CODE (operands[3]),
16934 GET_MODE (operands[3]),
16937 ix86_free_from_memory (GET_MODE (operands[2]));
16941 ;; FPU special functions.
16943 ;; This pattern implements a no-op XFmode truncation for
16944 ;; all fancy i386 XFmode math functions.
16946 (define_insn "truncxf<mode>2_i387_noop_unspec"
16947 [(set (match_operand:MODEF 0 "register_operand" "=f")
16948 (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
16949 UNSPEC_TRUNC_NOOP))]
16950 "TARGET_USE_FANCY_MATH_387"
16951 "* return output_387_reg_move (insn, operands);"
16952 [(set_attr "type" "fmov")
16953 (set_attr "mode" "<MODE>")])
16955 (define_insn "sqrtxf2"
16956 [(set (match_operand:XF 0 "register_operand" "=f")
16957 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
16958 "TARGET_USE_FANCY_MATH_387"
16960 [(set_attr "type" "fpspc")
16961 (set_attr "mode" "XF")
16962 (set_attr "athlon_decode" "direct")
16963 (set_attr "amdfam10_decode" "direct")])
16965 (define_insn "sqrt_extend<mode>xf2_i387"
16966 [(set (match_operand:XF 0 "register_operand" "=f")
16969 (match_operand:MODEF 1 "register_operand" "0"))))]
16970 "TARGET_USE_FANCY_MATH_387"
16972 [(set_attr "type" "fpspc")
16973 (set_attr "mode" "XF")
16974 (set_attr "athlon_decode" "direct")
16975 (set_attr "amdfam10_decode" "direct")])
16977 (define_insn "*rsqrtsf2_sse"
16978 [(set (match_operand:SF 0 "register_operand" "=x")
16979 (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
16982 "%vrsqrtss\t{%1, %d0|%d0, %1}"
16983 [(set_attr "type" "sse")
16984 (set_attr "atom_sse_attr" "rcp")
16985 (set_attr "prefix" "maybe_vex")
16986 (set_attr "mode" "SF")])
16988 (define_expand "rsqrtsf2"
16989 [(set (match_operand:SF 0 "register_operand" "")
16990 (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
16994 ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
16998 (define_insn "*sqrt<mode>2_sse"
16999 [(set (match_operand:MODEF 0 "register_operand" "=x")
17001 (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
17002 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
17003 "%vsqrts<ssemodefsuffix>\t{%1, %d0|%d0, %1}"
17004 [(set_attr "type" "sse")
17005 (set_attr "atom_sse_attr" "sqrt")
17006 (set_attr "prefix" "maybe_vex")
17007 (set_attr "mode" "<MODE>")
17008 (set_attr "athlon_decode" "*")
17009 (set_attr "amdfam10_decode" "*")])
17011 (define_expand "sqrt<mode>2"
17012 [(set (match_operand:MODEF 0 "register_operand" "")
17014 (match_operand:MODEF 1 "nonimmediate_operand" "")))]
17015 "(TARGET_USE_FANCY_MATH_387 && X87_ENABLE_ARITH (<MODE>mode))
17016 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
17018 if (<MODE>mode == SFmode
17019 && TARGET_SSE_MATH && TARGET_RECIP && !optimize_function_for_size_p (cfun)
17020 && flag_finite_math_only && !flag_trapping_math
17021 && flag_unsafe_math_optimizations)
17023 ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
17027 if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
17029 rtx op0 = gen_reg_rtx (XFmode);
17030 rtx op1 = force_reg (<MODE>mode, operands[1]);
17032 emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
17033 emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
17038 (define_insn "fpremxf4_i387"
17039 [(set (match_operand:XF 0 "register_operand" "=f")
17040 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
17041 (match_operand:XF 3 "register_operand" "1")]
17043 (set (match_operand:XF 1 "register_operand" "=u")
17044 (unspec:XF [(match_dup 2) (match_dup 3)]
17046 (set (reg:CCFP FPSR_REG)
17047 (unspec:CCFP [(match_dup 2) (match_dup 3)]
17049 "TARGET_USE_FANCY_MATH_387"
17051 [(set_attr "type" "fpspc")
17052 (set_attr "mode" "XF")])
17054 (define_expand "fmodxf3"
17055 [(use (match_operand:XF 0 "register_operand" ""))
17056 (use (match_operand:XF 1 "general_operand" ""))
17057 (use (match_operand:XF 2 "general_operand" ""))]
17058 "TARGET_USE_FANCY_MATH_387"
17060 rtx label = gen_label_rtx ();
17062 rtx op1 = gen_reg_rtx (XFmode);
17063 rtx op2 = gen_reg_rtx (XFmode);
17065 emit_move_insn (op2, operands[2]);
17066 emit_move_insn (op1, operands[1]);
17068 emit_label (label);
17069 emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
17070 ix86_emit_fp_unordered_jump (label);
17071 LABEL_NUSES (label) = 1;
17073 emit_move_insn (operands[0], op1);
17077 (define_expand "fmod<mode>3"
17078 [(use (match_operand:MODEF 0 "register_operand" ""))
17079 (use (match_operand:MODEF 1 "general_operand" ""))
17080 (use (match_operand:MODEF 2 "general_operand" ""))]
17081 "TARGET_USE_FANCY_MATH_387"
17083 rtx label = gen_label_rtx ();
17085 rtx op1 = gen_reg_rtx (XFmode);
17086 rtx op2 = gen_reg_rtx (XFmode);
17088 emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
17089 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17091 emit_label (label);
17092 emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
17093 ix86_emit_fp_unordered_jump (label);
17094 LABEL_NUSES (label) = 1;
17096 /* Truncate the result properly for strict SSE math. */
17097 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17098 && !TARGET_MIX_SSE_I387)
17099 emit_insn (gen_truncxf<mode>2 (operands[0], op1));
17101 emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
17106 (define_insn "fprem1xf4_i387"
17107 [(set (match_operand:XF 0 "register_operand" "=f")
17108 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
17109 (match_operand:XF 3 "register_operand" "1")]
17111 (set (match_operand:XF 1 "register_operand" "=u")
17112 (unspec:XF [(match_dup 2) (match_dup 3)]
17114 (set (reg:CCFP FPSR_REG)
17115 (unspec:CCFP [(match_dup 2) (match_dup 3)]
17117 "TARGET_USE_FANCY_MATH_387"
17119 [(set_attr "type" "fpspc")
17120 (set_attr "mode" "XF")])
17122 (define_expand "remainderxf3"
17123 [(use (match_operand:XF 0 "register_operand" ""))
17124 (use (match_operand:XF 1 "general_operand" ""))
17125 (use (match_operand:XF 2 "general_operand" ""))]
17126 "TARGET_USE_FANCY_MATH_387"
17128 rtx label = gen_label_rtx ();
17130 rtx op1 = gen_reg_rtx (XFmode);
17131 rtx op2 = gen_reg_rtx (XFmode);
17133 emit_move_insn (op2, operands[2]);
17134 emit_move_insn (op1, operands[1]);
17136 emit_label (label);
17137 emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
17138 ix86_emit_fp_unordered_jump (label);
17139 LABEL_NUSES (label) = 1;
17141 emit_move_insn (operands[0], op1);
17145 (define_expand "remainder<mode>3"
17146 [(use (match_operand:MODEF 0 "register_operand" ""))
17147 (use (match_operand:MODEF 1 "general_operand" ""))
17148 (use (match_operand:MODEF 2 "general_operand" ""))]
17149 "TARGET_USE_FANCY_MATH_387"
17151 rtx label = gen_label_rtx ();
17153 rtx op1 = gen_reg_rtx (XFmode);
17154 rtx op2 = gen_reg_rtx (XFmode);
17156 emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
17157 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17159 emit_label (label);
17161 emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
17162 ix86_emit_fp_unordered_jump (label);
17163 LABEL_NUSES (label) = 1;
17165 /* Truncate the result properly for strict SSE math. */
17166 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17167 && !TARGET_MIX_SSE_I387)
17168 emit_insn (gen_truncxf<mode>2 (operands[0], op1));
17170 emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
17175 (define_insn "*sinxf2_i387"
17176 [(set (match_operand:XF 0 "register_operand" "=f")
17177 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
17178 "TARGET_USE_FANCY_MATH_387
17179 && flag_unsafe_math_optimizations"
17181 [(set_attr "type" "fpspc")
17182 (set_attr "mode" "XF")])
17184 (define_insn "*sin_extend<mode>xf2_i387"
17185 [(set (match_operand:XF 0 "register_operand" "=f")
17186 (unspec:XF [(float_extend:XF
17187 (match_operand:MODEF 1 "register_operand" "0"))]
17189 "TARGET_USE_FANCY_MATH_387
17190 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17191 || TARGET_MIX_SSE_I387)
17192 && flag_unsafe_math_optimizations"
17194 [(set_attr "type" "fpspc")
17195 (set_attr "mode" "XF")])
17197 (define_insn "*cosxf2_i387"
17198 [(set (match_operand:XF 0 "register_operand" "=f")
17199 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
17200 "TARGET_USE_FANCY_MATH_387
17201 && flag_unsafe_math_optimizations"
17203 [(set_attr "type" "fpspc")
17204 (set_attr "mode" "XF")])
17206 (define_insn "*cos_extend<mode>xf2_i387"
17207 [(set (match_operand:XF 0 "register_operand" "=f")
17208 (unspec:XF [(float_extend:XF
17209 (match_operand:MODEF 1 "register_operand" "0"))]
17211 "TARGET_USE_FANCY_MATH_387
17212 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17213 || TARGET_MIX_SSE_I387)
17214 && flag_unsafe_math_optimizations"
17216 [(set_attr "type" "fpspc")
17217 (set_attr "mode" "XF")])
17219 ;; When sincos pattern is defined, sin and cos builtin functions will be
17220 ;; expanded to sincos pattern with one of its outputs left unused.
17221 ;; CSE pass will figure out if two sincos patterns can be combined,
17222 ;; otherwise sincos pattern will be split back to sin or cos pattern,
17223 ;; depending on the unused output.
17225 (define_insn "sincosxf3"
17226 [(set (match_operand:XF 0 "register_operand" "=f")
17227 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
17228 UNSPEC_SINCOS_COS))
17229 (set (match_operand:XF 1 "register_operand" "=u")
17230 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
17231 "TARGET_USE_FANCY_MATH_387
17232 && flag_unsafe_math_optimizations"
17234 [(set_attr "type" "fpspc")
17235 (set_attr "mode" "XF")])
17238 [(set (match_operand:XF 0 "register_operand" "")
17239 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
17240 UNSPEC_SINCOS_COS))
17241 (set (match_operand:XF 1 "register_operand" "")
17242 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
17243 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
17244 && !(reload_completed || reload_in_progress)"
17245 [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
17249 [(set (match_operand:XF 0 "register_operand" "")
17250 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
17251 UNSPEC_SINCOS_COS))
17252 (set (match_operand:XF 1 "register_operand" "")
17253 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
17254 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
17255 && !(reload_completed || reload_in_progress)"
17256 [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
17259 (define_insn "sincos_extend<mode>xf3_i387"
17260 [(set (match_operand:XF 0 "register_operand" "=f")
17261 (unspec:XF [(float_extend:XF
17262 (match_operand:MODEF 2 "register_operand" "0"))]
17263 UNSPEC_SINCOS_COS))
17264 (set (match_operand:XF 1 "register_operand" "=u")
17265 (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
17266 "TARGET_USE_FANCY_MATH_387
17267 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17268 || TARGET_MIX_SSE_I387)
17269 && flag_unsafe_math_optimizations"
17271 [(set_attr "type" "fpspc")
17272 (set_attr "mode" "XF")])
17275 [(set (match_operand:XF 0 "register_operand" "")
17276 (unspec:XF [(float_extend:XF
17277 (match_operand:MODEF 2 "register_operand" ""))]
17278 UNSPEC_SINCOS_COS))
17279 (set (match_operand:XF 1 "register_operand" "")
17280 (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
17281 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
17282 && !(reload_completed || reload_in_progress)"
17283 [(set (match_dup 1) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))]
17287 [(set (match_operand:XF 0 "register_operand" "")
17288 (unspec:XF [(float_extend:XF
17289 (match_operand:MODEF 2 "register_operand" ""))]
17290 UNSPEC_SINCOS_COS))
17291 (set (match_operand:XF 1 "register_operand" "")
17292 (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
17293 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
17294 && !(reload_completed || reload_in_progress)"
17295 [(set (match_dup 0) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))]
17298 (define_expand "sincos<mode>3"
17299 [(use (match_operand:MODEF 0 "register_operand" ""))
17300 (use (match_operand:MODEF 1 "register_operand" ""))
17301 (use (match_operand:MODEF 2 "register_operand" ""))]
17302 "TARGET_USE_FANCY_MATH_387
17303 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17304 || TARGET_MIX_SSE_I387)
17305 && flag_unsafe_math_optimizations"
17307 rtx op0 = gen_reg_rtx (XFmode);
17308 rtx op1 = gen_reg_rtx (XFmode);
17310 emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
17311 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17312 emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
17316 (define_insn "fptanxf4_i387"
17317 [(set (match_operand:XF 0 "register_operand" "=f")
17318 (match_operand:XF 3 "const_double_operand" "F"))
17319 (set (match_operand:XF 1 "register_operand" "=u")
17320 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
17322 "TARGET_USE_FANCY_MATH_387
17323 && flag_unsafe_math_optimizations
17324 && standard_80387_constant_p (operands[3]) == 2"
17326 [(set_attr "type" "fpspc")
17327 (set_attr "mode" "XF")])
17329 (define_insn "fptan_extend<mode>xf4_i387"
17330 [(set (match_operand:MODEF 0 "register_operand" "=f")
17331 (match_operand:MODEF 3 "const_double_operand" "F"))
17332 (set (match_operand:XF 1 "register_operand" "=u")
17333 (unspec:XF [(float_extend:XF
17334 (match_operand:MODEF 2 "register_operand" "0"))]
17336 "TARGET_USE_FANCY_MATH_387
17337 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17338 || TARGET_MIX_SSE_I387)
17339 && flag_unsafe_math_optimizations
17340 && standard_80387_constant_p (operands[3]) == 2"
17342 [(set_attr "type" "fpspc")
17343 (set_attr "mode" "XF")])
17345 (define_expand "tanxf2"
17346 [(use (match_operand:XF 0 "register_operand" ""))
17347 (use (match_operand:XF 1 "register_operand" ""))]
17348 "TARGET_USE_FANCY_MATH_387
17349 && flag_unsafe_math_optimizations"
17351 rtx one = gen_reg_rtx (XFmode);
17352 rtx op2 = CONST1_RTX (XFmode); /* fld1 */
17354 emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
17358 (define_expand "tan<mode>2"
17359 [(use (match_operand:MODEF 0 "register_operand" ""))
17360 (use (match_operand:MODEF 1 "register_operand" ""))]
17361 "TARGET_USE_FANCY_MATH_387
17362 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17363 || TARGET_MIX_SSE_I387)
17364 && flag_unsafe_math_optimizations"
17366 rtx op0 = gen_reg_rtx (XFmode);
17368 rtx one = gen_reg_rtx (<MODE>mode);
17369 rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
17371 emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
17372 operands[1], op2));
17373 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17377 (define_insn "*fpatanxf3_i387"
17378 [(set (match_operand:XF 0 "register_operand" "=f")
17379 (unspec:XF [(match_operand:XF 1 "register_operand" "0")
17380 (match_operand:XF 2 "register_operand" "u")]
17382 (clobber (match_scratch:XF 3 "=2"))]
17383 "TARGET_USE_FANCY_MATH_387
17384 && flag_unsafe_math_optimizations"
17386 [(set_attr "type" "fpspc")
17387 (set_attr "mode" "XF")])
17389 (define_insn "fpatan_extend<mode>xf3_i387"
17390 [(set (match_operand:XF 0 "register_operand" "=f")
17391 (unspec:XF [(float_extend:XF
17392 (match_operand:MODEF 1 "register_operand" "0"))
17394 (match_operand:MODEF 2 "register_operand" "u"))]
17396 (clobber (match_scratch:XF 3 "=2"))]
17397 "TARGET_USE_FANCY_MATH_387
17398 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17399 || TARGET_MIX_SSE_I387)
17400 && flag_unsafe_math_optimizations"
17402 [(set_attr "type" "fpspc")
17403 (set_attr "mode" "XF")])
17405 (define_expand "atan2xf3"
17406 [(parallel [(set (match_operand:XF 0 "register_operand" "")
17407 (unspec:XF [(match_operand:XF 2 "register_operand" "")
17408 (match_operand:XF 1 "register_operand" "")]
17410 (clobber (match_scratch:XF 3 ""))])]
17411 "TARGET_USE_FANCY_MATH_387
17412 && flag_unsafe_math_optimizations"
17415 (define_expand "atan2<mode>3"
17416 [(use (match_operand:MODEF 0 "register_operand" ""))
17417 (use (match_operand:MODEF 1 "register_operand" ""))
17418 (use (match_operand:MODEF 2 "register_operand" ""))]
17419 "TARGET_USE_FANCY_MATH_387
17420 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17421 || TARGET_MIX_SSE_I387)
17422 && flag_unsafe_math_optimizations"
17424 rtx op0 = gen_reg_rtx (XFmode);
17426 emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
17427 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17431 (define_expand "atanxf2"
17432 [(parallel [(set (match_operand:XF 0 "register_operand" "")
17433 (unspec:XF [(match_dup 2)
17434 (match_operand:XF 1 "register_operand" "")]
17436 (clobber (match_scratch:XF 3 ""))])]
17437 "TARGET_USE_FANCY_MATH_387
17438 && flag_unsafe_math_optimizations"
17440 operands[2] = gen_reg_rtx (XFmode);
17441 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
17444 (define_expand "atan<mode>2"
17445 [(use (match_operand:MODEF 0 "register_operand" ""))
17446 (use (match_operand:MODEF 1 "register_operand" ""))]
17447 "TARGET_USE_FANCY_MATH_387
17448 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17449 || TARGET_MIX_SSE_I387)
17450 && flag_unsafe_math_optimizations"
17452 rtx op0 = gen_reg_rtx (XFmode);
17454 rtx op2 = gen_reg_rtx (<MODE>mode);
17455 emit_move_insn (op2, CONST1_RTX (<MODE>mode)); /* fld1 */
17457 emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
17458 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17462 (define_expand "asinxf2"
17463 [(set (match_dup 2)
17464 (mult:XF (match_operand:XF 1 "register_operand" "")
17466 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
17467 (set (match_dup 5) (sqrt:XF (match_dup 4)))
17468 (parallel [(set (match_operand:XF 0 "register_operand" "")
17469 (unspec:XF [(match_dup 5) (match_dup 1)]
17471 (clobber (match_scratch:XF 6 ""))])]
17472 "TARGET_USE_FANCY_MATH_387
17473 && flag_unsafe_math_optimizations"
17477 if (optimize_insn_for_size_p ())
17480 for (i = 2; i < 6; i++)
17481 operands[i] = gen_reg_rtx (XFmode);
17483 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
17486 (define_expand "asin<mode>2"
17487 [(use (match_operand:MODEF 0 "register_operand" ""))
17488 (use (match_operand:MODEF 1 "general_operand" ""))]
17489 "TARGET_USE_FANCY_MATH_387
17490 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17491 || TARGET_MIX_SSE_I387)
17492 && flag_unsafe_math_optimizations"
17494 rtx op0 = gen_reg_rtx (XFmode);
17495 rtx op1 = gen_reg_rtx (XFmode);
17497 if (optimize_insn_for_size_p ())
17500 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17501 emit_insn (gen_asinxf2 (op0, op1));
17502 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17506 (define_expand "acosxf2"
17507 [(set (match_dup 2)
17508 (mult:XF (match_operand:XF 1 "register_operand" "")
17510 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
17511 (set (match_dup 5) (sqrt:XF (match_dup 4)))
17512 (parallel [(set (match_operand:XF 0 "register_operand" "")
17513 (unspec:XF [(match_dup 1) (match_dup 5)]
17515 (clobber (match_scratch:XF 6 ""))])]
17516 "TARGET_USE_FANCY_MATH_387
17517 && flag_unsafe_math_optimizations"
17521 if (optimize_insn_for_size_p ())
17524 for (i = 2; i < 6; i++)
17525 operands[i] = gen_reg_rtx (XFmode);
17527 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
17530 (define_expand "acos<mode>2"
17531 [(use (match_operand:MODEF 0 "register_operand" ""))
17532 (use (match_operand:MODEF 1 "general_operand" ""))]
17533 "TARGET_USE_FANCY_MATH_387
17534 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17535 || TARGET_MIX_SSE_I387)
17536 && flag_unsafe_math_optimizations"
17538 rtx op0 = gen_reg_rtx (XFmode);
17539 rtx op1 = gen_reg_rtx (XFmode);
17541 if (optimize_insn_for_size_p ())
17544 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17545 emit_insn (gen_acosxf2 (op0, op1));
17546 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17550 (define_insn "fyl2xxf3_i387"
17551 [(set (match_operand:XF 0 "register_operand" "=f")
17552 (unspec:XF [(match_operand:XF 1 "register_operand" "0")
17553 (match_operand:XF 2 "register_operand" "u")]
17555 (clobber (match_scratch:XF 3 "=2"))]
17556 "TARGET_USE_FANCY_MATH_387
17557 && flag_unsafe_math_optimizations"
17559 [(set_attr "type" "fpspc")
17560 (set_attr "mode" "XF")])
17562 (define_insn "fyl2x_extend<mode>xf3_i387"
17563 [(set (match_operand:XF 0 "register_operand" "=f")
17564 (unspec:XF [(float_extend:XF
17565 (match_operand:MODEF 1 "register_operand" "0"))
17566 (match_operand:XF 2 "register_operand" "u")]
17568 (clobber (match_scratch:XF 3 "=2"))]
17569 "TARGET_USE_FANCY_MATH_387
17570 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17571 || TARGET_MIX_SSE_I387)
17572 && flag_unsafe_math_optimizations"
17574 [(set_attr "type" "fpspc")
17575 (set_attr "mode" "XF")])
17577 (define_expand "logxf2"
17578 [(parallel [(set (match_operand:XF 0 "register_operand" "")
17579 (unspec:XF [(match_operand:XF 1 "register_operand" "")
17580 (match_dup 2)] UNSPEC_FYL2X))
17581 (clobber (match_scratch:XF 3 ""))])]
17582 "TARGET_USE_FANCY_MATH_387
17583 && flag_unsafe_math_optimizations"
17585 operands[2] = gen_reg_rtx (XFmode);
17586 emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
17589 (define_expand "log<mode>2"
17590 [(use (match_operand:MODEF 0 "register_operand" ""))
17591 (use (match_operand:MODEF 1 "register_operand" ""))]
17592 "TARGET_USE_FANCY_MATH_387
17593 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17594 || TARGET_MIX_SSE_I387)
17595 && flag_unsafe_math_optimizations"
17597 rtx op0 = gen_reg_rtx (XFmode);
17599 rtx op2 = gen_reg_rtx (XFmode);
17600 emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
17602 emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17603 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17607 (define_expand "log10xf2"
17608 [(parallel [(set (match_operand:XF 0 "register_operand" "")
17609 (unspec:XF [(match_operand:XF 1 "register_operand" "")
17610 (match_dup 2)] UNSPEC_FYL2X))
17611 (clobber (match_scratch:XF 3 ""))])]
17612 "TARGET_USE_FANCY_MATH_387
17613 && flag_unsafe_math_optimizations"
17615 operands[2] = gen_reg_rtx (XFmode);
17616 emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
17619 (define_expand "log10<mode>2"
17620 [(use (match_operand:MODEF 0 "register_operand" ""))
17621 (use (match_operand:MODEF 1 "register_operand" ""))]
17622 "TARGET_USE_FANCY_MATH_387
17623 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17624 || TARGET_MIX_SSE_I387)
17625 && flag_unsafe_math_optimizations"
17627 rtx op0 = gen_reg_rtx (XFmode);
17629 rtx op2 = gen_reg_rtx (XFmode);
17630 emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
17632 emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17633 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17637 (define_expand "log2xf2"
17638 [(parallel [(set (match_operand:XF 0 "register_operand" "")
17639 (unspec:XF [(match_operand:XF 1 "register_operand" "")
17640 (match_dup 2)] UNSPEC_FYL2X))
17641 (clobber (match_scratch:XF 3 ""))])]
17642 "TARGET_USE_FANCY_MATH_387
17643 && flag_unsafe_math_optimizations"
17645 operands[2] = gen_reg_rtx (XFmode);
17646 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
17649 (define_expand "log2<mode>2"
17650 [(use (match_operand:MODEF 0 "register_operand" ""))
17651 (use (match_operand:MODEF 1 "register_operand" ""))]
17652 "TARGET_USE_FANCY_MATH_387
17653 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17654 || TARGET_MIX_SSE_I387)
17655 && flag_unsafe_math_optimizations"
17657 rtx op0 = gen_reg_rtx (XFmode);
17659 rtx op2 = gen_reg_rtx (XFmode);
17660 emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
17662 emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17663 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17667 (define_insn "fyl2xp1xf3_i387"
17668 [(set (match_operand:XF 0 "register_operand" "=f")
17669 (unspec:XF [(match_operand:XF 1 "register_operand" "0")
17670 (match_operand:XF 2 "register_operand" "u")]
17672 (clobber (match_scratch:XF 3 "=2"))]
17673 "TARGET_USE_FANCY_MATH_387
17674 && flag_unsafe_math_optimizations"
17676 [(set_attr "type" "fpspc")
17677 (set_attr "mode" "XF")])
17679 (define_insn "fyl2xp1_extend<mode>xf3_i387"
17680 [(set (match_operand:XF 0 "register_operand" "=f")
17681 (unspec:XF [(float_extend:XF
17682 (match_operand:MODEF 1 "register_operand" "0"))
17683 (match_operand:XF 2 "register_operand" "u")]
17685 (clobber (match_scratch:XF 3 "=2"))]
17686 "TARGET_USE_FANCY_MATH_387
17687 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17688 || TARGET_MIX_SSE_I387)
17689 && flag_unsafe_math_optimizations"
17691 [(set_attr "type" "fpspc")
17692 (set_attr "mode" "XF")])
17694 (define_expand "log1pxf2"
17695 [(use (match_operand:XF 0 "register_operand" ""))
17696 (use (match_operand:XF 1 "register_operand" ""))]
17697 "TARGET_USE_FANCY_MATH_387
17698 && flag_unsafe_math_optimizations"
17700 if (optimize_insn_for_size_p ())
17703 ix86_emit_i387_log1p (operands[0], operands[1]);
17707 (define_expand "log1p<mode>2"
17708 [(use (match_operand:MODEF 0 "register_operand" ""))
17709 (use (match_operand:MODEF 1 "register_operand" ""))]
17710 "TARGET_USE_FANCY_MATH_387
17711 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17712 || TARGET_MIX_SSE_I387)
17713 && flag_unsafe_math_optimizations"
17717 if (optimize_insn_for_size_p ())
17720 op0 = gen_reg_rtx (XFmode);
17722 operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
17724 ix86_emit_i387_log1p (op0, operands[1]);
17725 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17729 (define_insn "fxtractxf3_i387"
17730 [(set (match_operand:XF 0 "register_operand" "=f")
17731 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
17732 UNSPEC_XTRACT_FRACT))
17733 (set (match_operand:XF 1 "register_operand" "=u")
17734 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
17735 "TARGET_USE_FANCY_MATH_387
17736 && flag_unsafe_math_optimizations"
17738 [(set_attr "type" "fpspc")
17739 (set_attr "mode" "XF")])
17741 (define_insn "fxtract_extend<mode>xf3_i387"
17742 [(set (match_operand:XF 0 "register_operand" "=f")
17743 (unspec:XF [(float_extend:XF
17744 (match_operand:MODEF 2 "register_operand" "0"))]
17745 UNSPEC_XTRACT_FRACT))
17746 (set (match_operand:XF 1 "register_operand" "=u")
17747 (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
17748 "TARGET_USE_FANCY_MATH_387
17749 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17750 || TARGET_MIX_SSE_I387)
17751 && flag_unsafe_math_optimizations"
17753 [(set_attr "type" "fpspc")
17754 (set_attr "mode" "XF")])
17756 (define_expand "logbxf2"
17757 [(parallel [(set (match_dup 2)
17758 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17759 UNSPEC_XTRACT_FRACT))
17760 (set (match_operand:XF 0 "register_operand" "")
17761 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
17762 "TARGET_USE_FANCY_MATH_387
17763 && flag_unsafe_math_optimizations"
17765 operands[2] = gen_reg_rtx (XFmode);
17768 (define_expand "logb<mode>2"
17769 [(use (match_operand:MODEF 0 "register_operand" ""))
17770 (use (match_operand:MODEF 1 "register_operand" ""))]
17771 "TARGET_USE_FANCY_MATH_387
17772 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17773 || TARGET_MIX_SSE_I387)
17774 && flag_unsafe_math_optimizations"
17776 rtx op0 = gen_reg_rtx (XFmode);
17777 rtx op1 = gen_reg_rtx (XFmode);
17779 emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17780 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
17784 (define_expand "ilogbxf2"
17785 [(use (match_operand:SI 0 "register_operand" ""))
17786 (use (match_operand:XF 1 "register_operand" ""))]
17787 "TARGET_USE_FANCY_MATH_387
17788 && flag_unsafe_math_optimizations"
17792 if (optimize_insn_for_size_p ())
17795 op0 = gen_reg_rtx (XFmode);
17796 op1 = gen_reg_rtx (XFmode);
17798 emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
17799 emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17803 (define_expand "ilogb<mode>2"
17804 [(use (match_operand:SI 0 "register_operand" ""))
17805 (use (match_operand:MODEF 1 "register_operand" ""))]
17806 "TARGET_USE_FANCY_MATH_387
17807 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17808 || TARGET_MIX_SSE_I387)
17809 && flag_unsafe_math_optimizations"
17813 if (optimize_insn_for_size_p ())
17816 op0 = gen_reg_rtx (XFmode);
17817 op1 = gen_reg_rtx (XFmode);
17819 emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17820 emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17824 (define_insn "*f2xm1xf2_i387"
17825 [(set (match_operand:XF 0 "register_operand" "=f")
17826 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17828 "TARGET_USE_FANCY_MATH_387
17829 && flag_unsafe_math_optimizations"
17831 [(set_attr "type" "fpspc")
17832 (set_attr "mode" "XF")])
17834 (define_insn "*fscalexf4_i387"
17835 [(set (match_operand:XF 0 "register_operand" "=f")
17836 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
17837 (match_operand:XF 3 "register_operand" "1")]
17838 UNSPEC_FSCALE_FRACT))
17839 (set (match_operand:XF 1 "register_operand" "=u")
17840 (unspec:XF [(match_dup 2) (match_dup 3)]
17841 UNSPEC_FSCALE_EXP))]
17842 "TARGET_USE_FANCY_MATH_387
17843 && flag_unsafe_math_optimizations"
17845 [(set_attr "type" "fpspc")
17846 (set_attr "mode" "XF")])
17848 (define_expand "expNcorexf3"
17849 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17850 (match_operand:XF 2 "register_operand" "")))
17851 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17852 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
17853 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
17854 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
17855 (parallel [(set (match_operand:XF 0 "register_operand" "")
17856 (unspec:XF [(match_dup 8) (match_dup 4)]
17857 UNSPEC_FSCALE_FRACT))
17859 (unspec:XF [(match_dup 8) (match_dup 4)]
17860 UNSPEC_FSCALE_EXP))])]
17861 "TARGET_USE_FANCY_MATH_387
17862 && flag_unsafe_math_optimizations"
17866 if (optimize_insn_for_size_p ())
17869 for (i = 3; i < 10; i++)
17870 operands[i] = gen_reg_rtx (XFmode);
17872 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
17875 (define_expand "expxf2"
17876 [(use (match_operand:XF 0 "register_operand" ""))
17877 (use (match_operand:XF 1 "register_operand" ""))]
17878 "TARGET_USE_FANCY_MATH_387
17879 && flag_unsafe_math_optimizations"
17883 if (optimize_insn_for_size_p ())
17886 op2 = gen_reg_rtx (XFmode);
17887 emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
17889 emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17893 (define_expand "exp<mode>2"
17894 [(use (match_operand:MODEF 0 "register_operand" ""))
17895 (use (match_operand:MODEF 1 "general_operand" ""))]
17896 "TARGET_USE_FANCY_MATH_387
17897 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17898 || TARGET_MIX_SSE_I387)
17899 && flag_unsafe_math_optimizations"
17903 if (optimize_insn_for_size_p ())
17906 op0 = gen_reg_rtx (XFmode);
17907 op1 = gen_reg_rtx (XFmode);
17909 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17910 emit_insn (gen_expxf2 (op0, op1));
17911 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17915 (define_expand "exp10xf2"
17916 [(use (match_operand:XF 0 "register_operand" ""))
17917 (use (match_operand:XF 1 "register_operand" ""))]
17918 "TARGET_USE_FANCY_MATH_387
17919 && flag_unsafe_math_optimizations"
17923 if (optimize_insn_for_size_p ())
17926 op2 = gen_reg_rtx (XFmode);
17927 emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
17929 emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17933 (define_expand "exp10<mode>2"
17934 [(use (match_operand:MODEF 0 "register_operand" ""))
17935 (use (match_operand:MODEF 1 "general_operand" ""))]
17936 "TARGET_USE_FANCY_MATH_387
17937 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17938 || TARGET_MIX_SSE_I387)
17939 && flag_unsafe_math_optimizations"
17943 if (optimize_insn_for_size_p ())
17946 op0 = gen_reg_rtx (XFmode);
17947 op1 = gen_reg_rtx (XFmode);
17949 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17950 emit_insn (gen_exp10xf2 (op0, op1));
17951 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17955 (define_expand "exp2xf2"
17956 [(use (match_operand:XF 0 "register_operand" ""))
17957 (use (match_operand:XF 1 "register_operand" ""))]
17958 "TARGET_USE_FANCY_MATH_387
17959 && flag_unsafe_math_optimizations"
17963 if (optimize_insn_for_size_p ())
17966 op2 = gen_reg_rtx (XFmode);
17967 emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
17969 emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17973 (define_expand "exp2<mode>2"
17974 [(use (match_operand:MODEF 0 "register_operand" ""))
17975 (use (match_operand:MODEF 1 "general_operand" ""))]
17976 "TARGET_USE_FANCY_MATH_387
17977 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17978 || TARGET_MIX_SSE_I387)
17979 && flag_unsafe_math_optimizations"
17983 if (optimize_insn_for_size_p ())
17986 op0 = gen_reg_rtx (XFmode);
17987 op1 = gen_reg_rtx (XFmode);
17989 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17990 emit_insn (gen_exp2xf2 (op0, op1));
17991 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17995 (define_expand "expm1xf2"
17996 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17998 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17999 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
18000 (set (match_dup 9) (float_extend:XF (match_dup 13)))
18001 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
18002 (parallel [(set (match_dup 7)
18003 (unspec:XF [(match_dup 6) (match_dup 4)]
18004 UNSPEC_FSCALE_FRACT))
18006 (unspec:XF [(match_dup 6) (match_dup 4)]
18007 UNSPEC_FSCALE_EXP))])
18008 (parallel [(set (match_dup 10)
18009 (unspec:XF [(match_dup 9) (match_dup 8)]
18010 UNSPEC_FSCALE_FRACT))
18011 (set (match_dup 11)
18012 (unspec:XF [(match_dup 9) (match_dup 8)]
18013 UNSPEC_FSCALE_EXP))])
18014 (set (match_dup 12) (minus:XF (match_dup 10)
18015 (float_extend:XF (match_dup 13))))
18016 (set (match_operand:XF 0 "register_operand" "")
18017 (plus:XF (match_dup 12) (match_dup 7)))]
18018 "TARGET_USE_FANCY_MATH_387
18019 && flag_unsafe_math_optimizations"
18023 if (optimize_insn_for_size_p ())
18026 for (i = 2; i < 13; i++)
18027 operands[i] = gen_reg_rtx (XFmode);
18030 = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
18032 emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
18035 (define_expand "expm1<mode>2"
18036 [(use (match_operand:MODEF 0 "register_operand" ""))
18037 (use (match_operand:MODEF 1 "general_operand" ""))]
18038 "TARGET_USE_FANCY_MATH_387
18039 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18040 || TARGET_MIX_SSE_I387)
18041 && flag_unsafe_math_optimizations"
18045 if (optimize_insn_for_size_p ())
18048 op0 = gen_reg_rtx (XFmode);
18049 op1 = gen_reg_rtx (XFmode);
18051 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18052 emit_insn (gen_expm1xf2 (op0, op1));
18053 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18057 (define_expand "ldexpxf3"
18058 [(set (match_dup 3)
18059 (float:XF (match_operand:SI 2 "register_operand" "")))
18060 (parallel [(set (match_operand:XF 0 " register_operand" "")
18061 (unspec:XF [(match_operand:XF 1 "register_operand" "")
18063 UNSPEC_FSCALE_FRACT))
18065 (unspec:XF [(match_dup 1) (match_dup 3)]
18066 UNSPEC_FSCALE_EXP))])]
18067 "TARGET_USE_FANCY_MATH_387
18068 && flag_unsafe_math_optimizations"
18070 if (optimize_insn_for_size_p ())
18073 operands[3] = gen_reg_rtx (XFmode);
18074 operands[4] = gen_reg_rtx (XFmode);
18077 (define_expand "ldexp<mode>3"
18078 [(use (match_operand:MODEF 0 "register_operand" ""))
18079 (use (match_operand:MODEF 1 "general_operand" ""))
18080 (use (match_operand:SI 2 "register_operand" ""))]
18081 "TARGET_USE_FANCY_MATH_387
18082 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18083 || TARGET_MIX_SSE_I387)
18084 && flag_unsafe_math_optimizations"
18088 if (optimize_insn_for_size_p ())
18091 op0 = gen_reg_rtx (XFmode);
18092 op1 = gen_reg_rtx (XFmode);
18094 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18095 emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
18096 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18100 (define_expand "scalbxf3"
18101 [(parallel [(set (match_operand:XF 0 " register_operand" "")
18102 (unspec:XF [(match_operand:XF 1 "register_operand" "")
18103 (match_operand:XF 2 "register_operand" "")]
18104 UNSPEC_FSCALE_FRACT))
18106 (unspec:XF [(match_dup 1) (match_dup 2)]
18107 UNSPEC_FSCALE_EXP))])]
18108 "TARGET_USE_FANCY_MATH_387
18109 && flag_unsafe_math_optimizations"
18111 if (optimize_insn_for_size_p ())
18114 operands[3] = gen_reg_rtx (XFmode);
18117 (define_expand "scalb<mode>3"
18118 [(use (match_operand:MODEF 0 "register_operand" ""))
18119 (use (match_operand:MODEF 1 "general_operand" ""))
18120 (use (match_operand:MODEF 2 "register_operand" ""))]
18121 "TARGET_USE_FANCY_MATH_387
18122 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18123 || TARGET_MIX_SSE_I387)
18124 && flag_unsafe_math_optimizations"
18128 if (optimize_insn_for_size_p ())
18131 op0 = gen_reg_rtx (XFmode);
18132 op1 = gen_reg_rtx (XFmode);
18133 op2 = gen_reg_rtx (XFmode);
18135 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18136 emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
18137 emit_insn (gen_scalbxf3 (op0, op1, op2));
18138 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18143 (define_insn "sse4_1_round<mode>2"
18144 [(set (match_operand:MODEF 0 "register_operand" "=x")
18145 (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
18146 (match_operand:SI 2 "const_0_to_15_operand" "n")]
18149 "%vrounds<ssemodefsuffix>\t{%2, %1, %d0|%d0, %1, %2}"
18150 [(set_attr "type" "ssecvt")
18151 (set_attr "prefix_extra" "1")
18152 (set_attr "prefix" "maybe_vex")
18153 (set_attr "mode" "<MODE>")])
18155 (define_insn "rintxf2"
18156 [(set (match_operand:XF 0 "register_operand" "=f")
18157 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18159 "TARGET_USE_FANCY_MATH_387
18160 && flag_unsafe_math_optimizations"
18162 [(set_attr "type" "fpspc")
18163 (set_attr "mode" "XF")])
18165 (define_expand "rint<mode>2"
18166 [(use (match_operand:MODEF 0 "register_operand" ""))
18167 (use (match_operand:MODEF 1 "register_operand" ""))]
18168 "(TARGET_USE_FANCY_MATH_387
18169 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18170 || TARGET_MIX_SSE_I387)
18171 && flag_unsafe_math_optimizations)
18172 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18173 && !flag_trapping_math)"
18175 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18176 && !flag_trapping_math)
18178 if (!TARGET_ROUND && optimize_insn_for_size_p ())
18181 emit_insn (gen_sse4_1_round<mode>2
18182 (operands[0], operands[1], GEN_INT (0x04)));
18184 ix86_expand_rint (operand0, operand1);
18188 rtx op0 = gen_reg_rtx (XFmode);
18189 rtx op1 = gen_reg_rtx (XFmode);
18191 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18192 emit_insn (gen_rintxf2 (op0, op1));
18194 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18199 (define_expand "round<mode>2"
18200 [(match_operand:MODEF 0 "register_operand" "")
18201 (match_operand:MODEF 1 "nonimmediate_operand" "")]
18202 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18203 && !flag_trapping_math && !flag_rounding_math"
18205 if (optimize_insn_for_size_p ())
18207 if (TARGET_64BIT || (<MODE>mode != DFmode))
18208 ix86_expand_round (operand0, operand1);
18210 ix86_expand_rounddf_32 (operand0, operand1);
18214 (define_insn_and_split "*fistdi2_1"
18215 [(set (match_operand:DI 0 "nonimmediate_operand" "")
18216 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18218 "TARGET_USE_FANCY_MATH_387
18219 && !(reload_completed || reload_in_progress)"
18224 if (memory_operand (operands[0], VOIDmode))
18225 emit_insn (gen_fistdi2 (operands[0], operands[1]));
18228 operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
18229 emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
18234 [(set_attr "type" "fpspc")
18235 (set_attr "mode" "DI")])
18237 (define_insn "fistdi2"
18238 [(set (match_operand:DI 0 "memory_operand" "=m")
18239 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
18241 (clobber (match_scratch:XF 2 "=&1f"))]
18242 "TARGET_USE_FANCY_MATH_387"
18243 "* return output_fix_trunc (insn, operands, 0);"
18244 [(set_attr "type" "fpspc")
18245 (set_attr "mode" "DI")])
18247 (define_insn "fistdi2_with_temp"
18248 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
18249 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
18251 (clobber (match_operand:DI 2 "memory_operand" "=X,m"))
18252 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
18253 "TARGET_USE_FANCY_MATH_387"
18255 [(set_attr "type" "fpspc")
18256 (set_attr "mode" "DI")])
18259 [(set (match_operand:DI 0 "register_operand" "")
18260 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18262 (clobber (match_operand:DI 2 "memory_operand" ""))
18263 (clobber (match_scratch 3 ""))]
18265 [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
18266 (clobber (match_dup 3))])
18267 (set (match_dup 0) (match_dup 2))]
18271 [(set (match_operand:DI 0 "memory_operand" "")
18272 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18274 (clobber (match_operand:DI 2 "memory_operand" ""))
18275 (clobber (match_scratch 3 ""))]
18277 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
18278 (clobber (match_dup 3))])]
18281 (define_insn_and_split "*fist<mode>2_1"
18282 [(set (match_operand:X87MODEI12 0 "register_operand" "")
18283 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18285 "TARGET_USE_FANCY_MATH_387
18286 && !(reload_completed || reload_in_progress)"
18291 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
18292 emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
18296 [(set_attr "type" "fpspc")
18297 (set_attr "mode" "<MODE>")])
18299 (define_insn "fist<mode>2"
18300 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
18301 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18303 "TARGET_USE_FANCY_MATH_387"
18304 "* return output_fix_trunc (insn, operands, 0);"
18305 [(set_attr "type" "fpspc")
18306 (set_attr "mode" "<MODE>")])
18308 (define_insn "fist<mode>2_with_temp"
18309 [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
18310 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18312 (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))]
18313 "TARGET_USE_FANCY_MATH_387"
18315 [(set_attr "type" "fpspc")
18316 (set_attr "mode" "<MODE>")])
18319 [(set (match_operand:X87MODEI12 0 "register_operand" "")
18320 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18322 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
18324 [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))
18325 (set (match_dup 0) (match_dup 2))]
18329 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18330 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18332 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
18334 [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))]
18337 (define_expand "lrintxf<mode>2"
18338 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18339 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18341 "TARGET_USE_FANCY_MATH_387"
18344 (define_expand "lrint<MODEF:mode><SSEMODEI24:mode>2"
18345 [(set (match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
18346 (unspec:SSEMODEI24 [(match_operand:MODEF 1 "register_operand" "")]
18347 UNSPEC_FIX_NOTRUNC))]
18348 "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
18349 && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)"
18352 (define_expand "lround<MODEF:mode><SSEMODEI24:mode>2"
18353 [(match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
18354 (match_operand:MODEF 1 "register_operand" "")]
18355 "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
18356 && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)
18357 && !flag_trapping_math && !flag_rounding_math"
18359 if (optimize_insn_for_size_p ())
18361 ix86_expand_lround (operand0, operand1);
18365 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18366 (define_insn_and_split "frndintxf2_floor"
18367 [(set (match_operand:XF 0 "register_operand" "")
18368 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18369 UNSPEC_FRNDINT_FLOOR))
18370 (clobber (reg:CC FLAGS_REG))]
18371 "TARGET_USE_FANCY_MATH_387
18372 && flag_unsafe_math_optimizations
18373 && !(reload_completed || reload_in_progress)"
18378 ix86_optimize_mode_switching[I387_FLOOR] = 1;
18380 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18381 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
18383 emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
18384 operands[2], operands[3]));
18387 [(set_attr "type" "frndint")
18388 (set_attr "i387_cw" "floor")
18389 (set_attr "mode" "XF")])
18391 (define_insn "frndintxf2_floor_i387"
18392 [(set (match_operand:XF 0 "register_operand" "=f")
18393 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18394 UNSPEC_FRNDINT_FLOOR))
18395 (use (match_operand:HI 2 "memory_operand" "m"))
18396 (use (match_operand:HI 3 "memory_operand" "m"))]
18397 "TARGET_USE_FANCY_MATH_387
18398 && flag_unsafe_math_optimizations"
18399 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18400 [(set_attr "type" "frndint")
18401 (set_attr "i387_cw" "floor")
18402 (set_attr "mode" "XF")])
18404 (define_expand "floorxf2"
18405 [(use (match_operand:XF 0 "register_operand" ""))
18406 (use (match_operand:XF 1 "register_operand" ""))]
18407 "TARGET_USE_FANCY_MATH_387
18408 && flag_unsafe_math_optimizations"
18410 if (optimize_insn_for_size_p ())
18412 emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
18416 (define_expand "floor<mode>2"
18417 [(use (match_operand:MODEF 0 "register_operand" ""))
18418 (use (match_operand:MODEF 1 "register_operand" ""))]
18419 "(TARGET_USE_FANCY_MATH_387
18420 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18421 || TARGET_MIX_SSE_I387)
18422 && flag_unsafe_math_optimizations)
18423 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18424 && !flag_trapping_math)"
18426 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18427 && !flag_trapping_math
18428 && (TARGET_ROUND || optimize_insn_for_speed_p ()))
18430 if (!TARGET_ROUND && optimize_insn_for_size_p ())
18433 emit_insn (gen_sse4_1_round<mode>2
18434 (operands[0], operands[1], GEN_INT (0x01)));
18435 else if (TARGET_64BIT || (<MODE>mode != DFmode))
18436 ix86_expand_floorceil (operand0, operand1, true);
18438 ix86_expand_floorceildf_32 (operand0, operand1, true);
18444 if (optimize_insn_for_size_p ())
18447 op0 = gen_reg_rtx (XFmode);
18448 op1 = gen_reg_rtx (XFmode);
18449 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18450 emit_insn (gen_frndintxf2_floor (op0, op1));
18452 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18457 (define_insn_and_split "*fist<mode>2_floor_1"
18458 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18459 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18460 UNSPEC_FIST_FLOOR))
18461 (clobber (reg:CC FLAGS_REG))]
18462 "TARGET_USE_FANCY_MATH_387
18463 && flag_unsafe_math_optimizations
18464 && !(reload_completed || reload_in_progress)"
18469 ix86_optimize_mode_switching[I387_FLOOR] = 1;
18471 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18472 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
18473 if (memory_operand (operands[0], VOIDmode))
18474 emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
18475 operands[2], operands[3]));
18478 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
18479 emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
18480 operands[2], operands[3],
18485 [(set_attr "type" "fistp")
18486 (set_attr "i387_cw" "floor")
18487 (set_attr "mode" "<MODE>")])
18489 (define_insn "fistdi2_floor"
18490 [(set (match_operand:DI 0 "memory_operand" "=m")
18491 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
18492 UNSPEC_FIST_FLOOR))
18493 (use (match_operand:HI 2 "memory_operand" "m"))
18494 (use (match_operand:HI 3 "memory_operand" "m"))
18495 (clobber (match_scratch:XF 4 "=&1f"))]
18496 "TARGET_USE_FANCY_MATH_387
18497 && flag_unsafe_math_optimizations"
18498 "* return output_fix_trunc (insn, operands, 0);"
18499 [(set_attr "type" "fistp")
18500 (set_attr "i387_cw" "floor")
18501 (set_attr "mode" "DI")])
18503 (define_insn "fistdi2_floor_with_temp"
18504 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
18505 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
18506 UNSPEC_FIST_FLOOR))
18507 (use (match_operand:HI 2 "memory_operand" "m,m"))
18508 (use (match_operand:HI 3 "memory_operand" "m,m"))
18509 (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
18510 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
18511 "TARGET_USE_FANCY_MATH_387
18512 && flag_unsafe_math_optimizations"
18514 [(set_attr "type" "fistp")
18515 (set_attr "i387_cw" "floor")
18516 (set_attr "mode" "DI")])
18519 [(set (match_operand:DI 0 "register_operand" "")
18520 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18521 UNSPEC_FIST_FLOOR))
18522 (use (match_operand:HI 2 "memory_operand" ""))
18523 (use (match_operand:HI 3 "memory_operand" ""))
18524 (clobber (match_operand:DI 4 "memory_operand" ""))
18525 (clobber (match_scratch 5 ""))]
18527 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
18528 (use (match_dup 2))
18529 (use (match_dup 3))
18530 (clobber (match_dup 5))])
18531 (set (match_dup 0) (match_dup 4))]
18535 [(set (match_operand:DI 0 "memory_operand" "")
18536 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18537 UNSPEC_FIST_FLOOR))
18538 (use (match_operand:HI 2 "memory_operand" ""))
18539 (use (match_operand:HI 3 "memory_operand" ""))
18540 (clobber (match_operand:DI 4 "memory_operand" ""))
18541 (clobber (match_scratch 5 ""))]
18543 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
18544 (use (match_dup 2))
18545 (use (match_dup 3))
18546 (clobber (match_dup 5))])]
18549 (define_insn "fist<mode>2_floor"
18550 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
18551 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18552 UNSPEC_FIST_FLOOR))
18553 (use (match_operand:HI 2 "memory_operand" "m"))
18554 (use (match_operand:HI 3 "memory_operand" "m"))]
18555 "TARGET_USE_FANCY_MATH_387
18556 && flag_unsafe_math_optimizations"
18557 "* return output_fix_trunc (insn, operands, 0);"
18558 [(set_attr "type" "fistp")
18559 (set_attr "i387_cw" "floor")
18560 (set_attr "mode" "<MODE>")])
18562 (define_insn "fist<mode>2_floor_with_temp"
18563 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
18564 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
18565 UNSPEC_FIST_FLOOR))
18566 (use (match_operand:HI 2 "memory_operand" "m,m"))
18567 (use (match_operand:HI 3 "memory_operand" "m,m"))
18568 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
18569 "TARGET_USE_FANCY_MATH_387
18570 && flag_unsafe_math_optimizations"
18572 [(set_attr "type" "fistp")
18573 (set_attr "i387_cw" "floor")
18574 (set_attr "mode" "<MODE>")])
18577 [(set (match_operand:X87MODEI12 0 "register_operand" "")
18578 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18579 UNSPEC_FIST_FLOOR))
18580 (use (match_operand:HI 2 "memory_operand" ""))
18581 (use (match_operand:HI 3 "memory_operand" ""))
18582 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18584 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
18585 UNSPEC_FIST_FLOOR))
18586 (use (match_dup 2))
18587 (use (match_dup 3))])
18588 (set (match_dup 0) (match_dup 4))]
18592 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18593 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18594 UNSPEC_FIST_FLOOR))
18595 (use (match_operand:HI 2 "memory_operand" ""))
18596 (use (match_operand:HI 3 "memory_operand" ""))
18597 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18599 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
18600 UNSPEC_FIST_FLOOR))
18601 (use (match_dup 2))
18602 (use (match_dup 3))])]
18605 (define_expand "lfloorxf<mode>2"
18606 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18607 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18608 UNSPEC_FIST_FLOOR))
18609 (clobber (reg:CC FLAGS_REG))])]
18610 "TARGET_USE_FANCY_MATH_387
18611 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
18612 && flag_unsafe_math_optimizations"
18615 (define_expand "lfloor<mode>di2"
18616 [(match_operand:DI 0 "nonimmediate_operand" "")
18617 (match_operand:MODEF 1 "register_operand" "")]
18618 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
18619 && !flag_trapping_math"
18621 if (optimize_insn_for_size_p ())
18623 ix86_expand_lfloorceil (operand0, operand1, true);
18627 (define_expand "lfloor<mode>si2"
18628 [(match_operand:SI 0 "nonimmediate_operand" "")
18629 (match_operand:MODEF 1 "register_operand" "")]
18630 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18631 && !flag_trapping_math"
18633 if (optimize_insn_for_size_p () && TARGET_64BIT)
18635 ix86_expand_lfloorceil (operand0, operand1, true);
18639 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18640 (define_insn_and_split "frndintxf2_ceil"
18641 [(set (match_operand:XF 0 "register_operand" "")
18642 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18643 UNSPEC_FRNDINT_CEIL))
18644 (clobber (reg:CC FLAGS_REG))]
18645 "TARGET_USE_FANCY_MATH_387
18646 && flag_unsafe_math_optimizations
18647 && !(reload_completed || reload_in_progress)"
18652 ix86_optimize_mode_switching[I387_CEIL] = 1;
18654 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18655 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
18657 emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
18658 operands[2], operands[3]));
18661 [(set_attr "type" "frndint")
18662 (set_attr "i387_cw" "ceil")
18663 (set_attr "mode" "XF")])
18665 (define_insn "frndintxf2_ceil_i387"
18666 [(set (match_operand:XF 0 "register_operand" "=f")
18667 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18668 UNSPEC_FRNDINT_CEIL))
18669 (use (match_operand:HI 2 "memory_operand" "m"))
18670 (use (match_operand:HI 3 "memory_operand" "m"))]
18671 "TARGET_USE_FANCY_MATH_387
18672 && flag_unsafe_math_optimizations"
18673 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18674 [(set_attr "type" "frndint")
18675 (set_attr "i387_cw" "ceil")
18676 (set_attr "mode" "XF")])
18678 (define_expand "ceilxf2"
18679 [(use (match_operand:XF 0 "register_operand" ""))
18680 (use (match_operand:XF 1 "register_operand" ""))]
18681 "TARGET_USE_FANCY_MATH_387
18682 && flag_unsafe_math_optimizations"
18684 if (optimize_insn_for_size_p ())
18686 emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
18690 (define_expand "ceil<mode>2"
18691 [(use (match_operand:MODEF 0 "register_operand" ""))
18692 (use (match_operand:MODEF 1 "register_operand" ""))]
18693 "(TARGET_USE_FANCY_MATH_387
18694 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18695 || TARGET_MIX_SSE_I387)
18696 && flag_unsafe_math_optimizations)
18697 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18698 && !flag_trapping_math)"
18700 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18701 && !flag_trapping_math
18702 && (TARGET_ROUND || optimize_insn_for_speed_p ()))
18705 emit_insn (gen_sse4_1_round<mode>2
18706 (operands[0], operands[1], GEN_INT (0x02)));
18707 else if (optimize_insn_for_size_p ())
18709 else if (TARGET_64BIT || (<MODE>mode != DFmode))
18710 ix86_expand_floorceil (operand0, operand1, false);
18712 ix86_expand_floorceildf_32 (operand0, operand1, false);
18718 if (optimize_insn_for_size_p ())
18721 op0 = gen_reg_rtx (XFmode);
18722 op1 = gen_reg_rtx (XFmode);
18723 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18724 emit_insn (gen_frndintxf2_ceil (op0, op1));
18726 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18731 (define_insn_and_split "*fist<mode>2_ceil_1"
18732 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18733 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18735 (clobber (reg:CC FLAGS_REG))]
18736 "TARGET_USE_FANCY_MATH_387
18737 && flag_unsafe_math_optimizations
18738 && !(reload_completed || reload_in_progress)"
18743 ix86_optimize_mode_switching[I387_CEIL] = 1;
18745 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18746 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
18747 if (memory_operand (operands[0], VOIDmode))
18748 emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
18749 operands[2], operands[3]));
18752 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
18753 emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
18754 operands[2], operands[3],
18759 [(set_attr "type" "fistp")
18760 (set_attr "i387_cw" "ceil")
18761 (set_attr "mode" "<MODE>")])
18763 (define_insn "fistdi2_ceil"
18764 [(set (match_operand:DI 0 "memory_operand" "=m")
18765 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
18767 (use (match_operand:HI 2 "memory_operand" "m"))
18768 (use (match_operand:HI 3 "memory_operand" "m"))
18769 (clobber (match_scratch:XF 4 "=&1f"))]
18770 "TARGET_USE_FANCY_MATH_387
18771 && flag_unsafe_math_optimizations"
18772 "* return output_fix_trunc (insn, operands, 0);"
18773 [(set_attr "type" "fistp")
18774 (set_attr "i387_cw" "ceil")
18775 (set_attr "mode" "DI")])
18777 (define_insn "fistdi2_ceil_with_temp"
18778 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
18779 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
18781 (use (match_operand:HI 2 "memory_operand" "m,m"))
18782 (use (match_operand:HI 3 "memory_operand" "m,m"))
18783 (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
18784 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
18785 "TARGET_USE_FANCY_MATH_387
18786 && flag_unsafe_math_optimizations"
18788 [(set_attr "type" "fistp")
18789 (set_attr "i387_cw" "ceil")
18790 (set_attr "mode" "DI")])
18793 [(set (match_operand:DI 0 "register_operand" "")
18794 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18796 (use (match_operand:HI 2 "memory_operand" ""))
18797 (use (match_operand:HI 3 "memory_operand" ""))
18798 (clobber (match_operand:DI 4 "memory_operand" ""))
18799 (clobber (match_scratch 5 ""))]
18801 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
18802 (use (match_dup 2))
18803 (use (match_dup 3))
18804 (clobber (match_dup 5))])
18805 (set (match_dup 0) (match_dup 4))]
18809 [(set (match_operand:DI 0 "memory_operand" "")
18810 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18812 (use (match_operand:HI 2 "memory_operand" ""))
18813 (use (match_operand:HI 3 "memory_operand" ""))
18814 (clobber (match_operand:DI 4 "memory_operand" ""))
18815 (clobber (match_scratch 5 ""))]
18817 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
18818 (use (match_dup 2))
18819 (use (match_dup 3))
18820 (clobber (match_dup 5))])]
18823 (define_insn "fist<mode>2_ceil"
18824 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
18825 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18827 (use (match_operand:HI 2 "memory_operand" "m"))
18828 (use (match_operand:HI 3 "memory_operand" "m"))]
18829 "TARGET_USE_FANCY_MATH_387
18830 && flag_unsafe_math_optimizations"
18831 "* return output_fix_trunc (insn, operands, 0);"
18832 [(set_attr "type" "fistp")
18833 (set_attr "i387_cw" "ceil")
18834 (set_attr "mode" "<MODE>")])
18836 (define_insn "fist<mode>2_ceil_with_temp"
18837 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
18838 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
18840 (use (match_operand:HI 2 "memory_operand" "m,m"))
18841 (use (match_operand:HI 3 "memory_operand" "m,m"))
18842 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
18843 "TARGET_USE_FANCY_MATH_387
18844 && flag_unsafe_math_optimizations"
18846 [(set_attr "type" "fistp")
18847 (set_attr "i387_cw" "ceil")
18848 (set_attr "mode" "<MODE>")])
18851 [(set (match_operand:X87MODEI12 0 "register_operand" "")
18852 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18854 (use (match_operand:HI 2 "memory_operand" ""))
18855 (use (match_operand:HI 3 "memory_operand" ""))
18856 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18858 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
18860 (use (match_dup 2))
18861 (use (match_dup 3))])
18862 (set (match_dup 0) (match_dup 4))]
18866 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18867 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18869 (use (match_operand:HI 2 "memory_operand" ""))
18870 (use (match_operand:HI 3 "memory_operand" ""))
18871 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18873 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
18875 (use (match_dup 2))
18876 (use (match_dup 3))])]
18879 (define_expand "lceilxf<mode>2"
18880 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18881 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18883 (clobber (reg:CC FLAGS_REG))])]
18884 "TARGET_USE_FANCY_MATH_387
18885 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
18886 && flag_unsafe_math_optimizations"
18889 (define_expand "lceil<mode>di2"
18890 [(match_operand:DI 0 "nonimmediate_operand" "")
18891 (match_operand:MODEF 1 "register_operand" "")]
18892 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
18893 && !flag_trapping_math"
18895 ix86_expand_lfloorceil (operand0, operand1, false);
18899 (define_expand "lceil<mode>si2"
18900 [(match_operand:SI 0 "nonimmediate_operand" "")
18901 (match_operand:MODEF 1 "register_operand" "")]
18902 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18903 && !flag_trapping_math"
18905 ix86_expand_lfloorceil (operand0, operand1, false);
18909 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18910 (define_insn_and_split "frndintxf2_trunc"
18911 [(set (match_operand:XF 0 "register_operand" "")
18912 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18913 UNSPEC_FRNDINT_TRUNC))
18914 (clobber (reg:CC FLAGS_REG))]
18915 "TARGET_USE_FANCY_MATH_387
18916 && flag_unsafe_math_optimizations
18917 && !(reload_completed || reload_in_progress)"
18922 ix86_optimize_mode_switching[I387_TRUNC] = 1;
18924 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18925 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
18927 emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
18928 operands[2], operands[3]));
18931 [(set_attr "type" "frndint")
18932 (set_attr "i387_cw" "trunc")
18933 (set_attr "mode" "XF")])
18935 (define_insn "frndintxf2_trunc_i387"
18936 [(set (match_operand:XF 0 "register_operand" "=f")
18937 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18938 UNSPEC_FRNDINT_TRUNC))
18939 (use (match_operand:HI 2 "memory_operand" "m"))
18940 (use (match_operand:HI 3 "memory_operand" "m"))]
18941 "TARGET_USE_FANCY_MATH_387
18942 && flag_unsafe_math_optimizations"
18943 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18944 [(set_attr "type" "frndint")
18945 (set_attr "i387_cw" "trunc")
18946 (set_attr "mode" "XF")])
18948 (define_expand "btruncxf2"
18949 [(use (match_operand:XF 0 "register_operand" ""))
18950 (use (match_operand:XF 1 "register_operand" ""))]
18951 "TARGET_USE_FANCY_MATH_387
18952 && flag_unsafe_math_optimizations"
18954 if (optimize_insn_for_size_p ())
18956 emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
18960 (define_expand "btrunc<mode>2"
18961 [(use (match_operand:MODEF 0 "register_operand" ""))
18962 (use (match_operand:MODEF 1 "register_operand" ""))]
18963 "(TARGET_USE_FANCY_MATH_387
18964 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18965 || TARGET_MIX_SSE_I387)
18966 && flag_unsafe_math_optimizations)
18967 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18968 && !flag_trapping_math)"
18970 if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18971 && !flag_trapping_math
18972 && (TARGET_ROUND || optimize_insn_for_speed_p ()))
18975 emit_insn (gen_sse4_1_round<mode>2
18976 (operands[0], operands[1], GEN_INT (0x03)));
18977 else if (optimize_insn_for_size_p ())
18979 else if (TARGET_64BIT || (<MODE>mode != DFmode))
18980 ix86_expand_trunc (operand0, operand1);
18982 ix86_expand_truncdf_32 (operand0, operand1);
18988 if (optimize_insn_for_size_p ())
18991 op0 = gen_reg_rtx (XFmode);
18992 op1 = gen_reg_rtx (XFmode);
18993 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18994 emit_insn (gen_frndintxf2_trunc (op0, op1));
18996 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
19001 ;; Rounding mode control word calculation could clobber FLAGS_REG.
19002 (define_insn_and_split "frndintxf2_mask_pm"
19003 [(set (match_operand:XF 0 "register_operand" "")
19004 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
19005 UNSPEC_FRNDINT_MASK_PM))
19006 (clobber (reg:CC FLAGS_REG))]
19007 "TARGET_USE_FANCY_MATH_387
19008 && flag_unsafe_math_optimizations
19009 && !(reload_completed || reload_in_progress)"
19014 ix86_optimize_mode_switching[I387_MASK_PM] = 1;
19016 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
19017 operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
19019 emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
19020 operands[2], operands[3]));
19023 [(set_attr "type" "frndint")
19024 (set_attr "i387_cw" "mask_pm")
19025 (set_attr "mode" "XF")])
19027 (define_insn "frndintxf2_mask_pm_i387"
19028 [(set (match_operand:XF 0 "register_operand" "=f")
19029 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
19030 UNSPEC_FRNDINT_MASK_PM))
19031 (use (match_operand:HI 2 "memory_operand" "m"))
19032 (use (match_operand:HI 3 "memory_operand" "m"))]
19033 "TARGET_USE_FANCY_MATH_387
19034 && flag_unsafe_math_optimizations"
19035 "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
19036 [(set_attr "type" "frndint")
19037 (set_attr "i387_cw" "mask_pm")
19038 (set_attr "mode" "XF")])
19040 (define_expand "nearbyintxf2"
19041 [(use (match_operand:XF 0 "register_operand" ""))
19042 (use (match_operand:XF 1 "register_operand" ""))]
19043 "TARGET_USE_FANCY_MATH_387
19044 && flag_unsafe_math_optimizations"
19046 emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
19051 (define_expand "nearbyint<mode>2"
19052 [(use (match_operand:MODEF 0 "register_operand" ""))
19053 (use (match_operand:MODEF 1 "register_operand" ""))]
19054 "TARGET_USE_FANCY_MATH_387
19055 && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
19056 || TARGET_MIX_SSE_I387)
19057 && flag_unsafe_math_optimizations"
19059 rtx op0 = gen_reg_rtx (XFmode);
19060 rtx op1 = gen_reg_rtx (XFmode);
19062 emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
19063 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
19065 emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
19069 (define_insn "fxam<mode>2_i387"
19070 [(set (match_operand:HI 0 "register_operand" "=a")
19072 [(match_operand:X87MODEF 1 "register_operand" "f")]
19074 "TARGET_USE_FANCY_MATH_387"
19075 "fxam\n\tfnstsw\t%0"
19076 [(set_attr "type" "multi")
19077 (set_attr "unit" "i387")
19078 (set_attr "mode" "<MODE>")])
19080 (define_insn_and_split "fxam<mode>2_i387_with_temp"
19081 [(set (match_operand:HI 0 "register_operand" "")
19083 [(match_operand:MODEF 1 "memory_operand" "")]
19085 "TARGET_USE_FANCY_MATH_387
19086 && !(reload_completed || reload_in_progress)"
19089 [(set (match_dup 2)(match_dup 1))
19091 (unspec:HI [(match_dup 2)] UNSPEC_FXAM))]
19093 operands[2] = gen_reg_rtx (<MODE>mode);
19095 MEM_VOLATILE_P (operands[1]) = 1;
19097 [(set_attr "type" "multi")
19098 (set_attr "unit" "i387")
19099 (set_attr "mode" "<MODE>")])
19101 (define_expand "isinfxf2"
19102 [(use (match_operand:SI 0 "register_operand" ""))
19103 (use (match_operand:XF 1 "register_operand" ""))]
19104 "TARGET_USE_FANCY_MATH_387
19105 && TARGET_C99_FUNCTIONS"
19107 rtx mask = GEN_INT (0x45);
19108 rtx val = GEN_INT (0x05);
19112 rtx scratch = gen_reg_rtx (HImode);
19113 rtx res = gen_reg_rtx (QImode);
19115 emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
19117 emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
19118 emit_insn (gen_cmpqi_ext_3 (scratch, val));
19119 cond = gen_rtx_fmt_ee (EQ, QImode,
19120 gen_rtx_REG (CCmode, FLAGS_REG),
19122 emit_insn (gen_rtx_SET (VOIDmode, res, cond));
19123 emit_insn (gen_zero_extendqisi2 (operands[0], res));
19127 (define_expand "isinf<mode>2"
19128 [(use (match_operand:SI 0 "register_operand" ""))
19129 (use (match_operand:MODEF 1 "nonimmediate_operand" ""))]
19130 "TARGET_USE_FANCY_MATH_387
19131 && TARGET_C99_FUNCTIONS
19132 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
19134 rtx mask = GEN_INT (0x45);
19135 rtx val = GEN_INT (0x05);
19139 rtx scratch = gen_reg_rtx (HImode);
19140 rtx res = gen_reg_rtx (QImode);
19142 /* Remove excess precision by forcing value through memory. */
19143 if (memory_operand (operands[1], VOIDmode))
19144 emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, operands[1]));
19147 enum ix86_stack_slot slot = (virtuals_instantiated
19150 rtx temp = assign_386_stack_local (<MODE>mode, slot);
19152 emit_move_insn (temp, operands[1]);
19153 emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, temp));
19156 emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
19157 emit_insn (gen_cmpqi_ext_3 (scratch, val));
19158 cond = gen_rtx_fmt_ee (EQ, QImode,
19159 gen_rtx_REG (CCmode, FLAGS_REG),
19161 emit_insn (gen_rtx_SET (VOIDmode, res, cond));
19162 emit_insn (gen_zero_extendqisi2 (operands[0], res));
19166 (define_expand "signbit<mode>2"
19167 [(use (match_operand:SI 0 "register_operand" ""))
19168 (use (match_operand:X87MODEF 1 "register_operand" ""))]
19169 "TARGET_USE_FANCY_MATH_387
19170 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
19172 rtx mask = GEN_INT (0x0200);
19174 rtx scratch = gen_reg_rtx (HImode);
19176 emit_insn (gen_fxam<mode>2_i387 (scratch, operands[1]));
19177 emit_insn (gen_andsi3 (operands[0], gen_lowpart (SImode, scratch), mask));
19181 ;; Block operation instructions
19184 [(unspec_volatile [(const_int 0)] UNSPECV_CLD)]
19187 [(set_attr "length" "1")
19188 (set_attr "length_immediate" "0")
19189 (set_attr "modrm" "0")])
19191 (define_expand "movmemsi"
19192 [(use (match_operand:BLK 0 "memory_operand" ""))
19193 (use (match_operand:BLK 1 "memory_operand" ""))
19194 (use (match_operand:SI 2 "nonmemory_operand" ""))
19195 (use (match_operand:SI 3 "const_int_operand" ""))
19196 (use (match_operand:SI 4 "const_int_operand" ""))
19197 (use (match_operand:SI 5 "const_int_operand" ""))]
19200 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
19201 operands[4], operands[5]))
19207 (define_expand "movmemdi"
19208 [(use (match_operand:BLK 0 "memory_operand" ""))
19209 (use (match_operand:BLK 1 "memory_operand" ""))
19210 (use (match_operand:DI 2 "nonmemory_operand" ""))
19211 (use (match_operand:DI 3 "const_int_operand" ""))
19212 (use (match_operand:SI 4 "const_int_operand" ""))
19213 (use (match_operand:SI 5 "const_int_operand" ""))]
19216 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
19217 operands[4], operands[5]))
19223 ;; Most CPUs don't like single string operations
19224 ;; Handle this case here to simplify previous expander.
19226 (define_expand "strmov"
19227 [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
19228 (set (match_operand 1 "memory_operand" "") (match_dup 4))
19229 (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
19230 (clobber (reg:CC FLAGS_REG))])
19231 (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
19232 (clobber (reg:CC FLAGS_REG))])]
19235 rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
19237 /* If .md ever supports :P for Pmode, these can be directly
19238 in the pattern above. */
19239 operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
19240 operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
19242 /* Can't use this if the user has appropriated esi or edi. */
19243 if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
19244 && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
19246 emit_insn (gen_strmov_singleop (operands[0], operands[1],
19247 operands[2], operands[3],
19248 operands[5], operands[6]));
19252 operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
19255 (define_expand "strmov_singleop"
19256 [(parallel [(set (match_operand 1 "memory_operand" "")
19257 (match_operand 3 "memory_operand" ""))
19258 (set (match_operand 0 "register_operand" "")
19259 (match_operand 4 "" ""))
19260 (set (match_operand 2 "register_operand" "")
19261 (match_operand 5 "" ""))])]
19263 "ix86_current_function_needs_cld = 1;")
19265 (define_insn "*strmovdi_rex_1"
19266 [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
19267 (mem:DI (match_operand:DI 3 "register_operand" "1")))
19268 (set (match_operand:DI 0 "register_operand" "=D")
19269 (plus:DI (match_dup 2)
19271 (set (match_operand:DI 1 "register_operand" "=S")
19272 (plus:DI (match_dup 3)
19276 [(set_attr "type" "str")
19277 (set_attr "mode" "DI")
19278 (set_attr "memory" "both")])
19280 (define_insn "*strmovsi_1"
19281 [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
19282 (mem:SI (match_operand:SI 3 "register_operand" "1")))
19283 (set (match_operand:SI 0 "register_operand" "=D")
19284 (plus:SI (match_dup 2)
19286 (set (match_operand:SI 1 "register_operand" "=S")
19287 (plus:SI (match_dup 3)
19291 [(set_attr "type" "str")
19292 (set_attr "mode" "SI")
19293 (set_attr "memory" "both")])
19295 (define_insn "*strmovsi_rex_1"
19296 [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
19297 (mem:SI (match_operand:DI 3 "register_operand" "1")))
19298 (set (match_operand:DI 0 "register_operand" "=D")
19299 (plus:DI (match_dup 2)
19301 (set (match_operand:DI 1 "register_operand" "=S")
19302 (plus:DI (match_dup 3)
19306 [(set_attr "type" "str")
19307 (set_attr "mode" "SI")
19308 (set_attr "memory" "both")])
19310 (define_insn "*strmovhi_1"
19311 [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
19312 (mem:HI (match_operand:SI 3 "register_operand" "1")))
19313 (set (match_operand:SI 0 "register_operand" "=D")
19314 (plus:SI (match_dup 2)
19316 (set (match_operand:SI 1 "register_operand" "=S")
19317 (plus:SI (match_dup 3)
19321 [(set_attr "type" "str")
19322 (set_attr "memory" "both")
19323 (set_attr "mode" "HI")])
19325 (define_insn "*strmovhi_rex_1"
19326 [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
19327 (mem:HI (match_operand:DI 3 "register_operand" "1")))
19328 (set (match_operand:DI 0 "register_operand" "=D")
19329 (plus:DI (match_dup 2)
19331 (set (match_operand:DI 1 "register_operand" "=S")
19332 (plus:DI (match_dup 3)
19336 [(set_attr "type" "str")
19337 (set_attr "memory" "both")
19338 (set_attr "mode" "HI")])
19340 (define_insn "*strmovqi_1"
19341 [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
19342 (mem:QI (match_operand:SI 3 "register_operand" "1")))
19343 (set (match_operand:SI 0 "register_operand" "=D")
19344 (plus:SI (match_dup 2)
19346 (set (match_operand:SI 1 "register_operand" "=S")
19347 (plus:SI (match_dup 3)
19351 [(set_attr "type" "str")
19352 (set_attr "memory" "both")
19353 (set_attr "mode" "QI")])
19355 (define_insn "*strmovqi_rex_1"
19356 [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
19357 (mem:QI (match_operand:DI 3 "register_operand" "1")))
19358 (set (match_operand:DI 0 "register_operand" "=D")
19359 (plus:DI (match_dup 2)
19361 (set (match_operand:DI 1 "register_operand" "=S")
19362 (plus:DI (match_dup 3)
19366 [(set_attr "type" "str")
19367 (set_attr "memory" "both")
19368 (set_attr "mode" "QI")])
19370 (define_expand "rep_mov"
19371 [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
19372 (set (match_operand 0 "register_operand" "")
19373 (match_operand 5 "" ""))
19374 (set (match_operand 2 "register_operand" "")
19375 (match_operand 6 "" ""))
19376 (set (match_operand 1 "memory_operand" "")
19377 (match_operand 3 "memory_operand" ""))
19378 (use (match_dup 4))])]
19380 "ix86_current_function_needs_cld = 1;")
19382 (define_insn "*rep_movdi_rex64"
19383 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
19384 (set (match_operand:DI 0 "register_operand" "=D")
19385 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
19387 (match_operand:DI 3 "register_operand" "0")))
19388 (set (match_operand:DI 1 "register_operand" "=S")
19389 (plus:DI (ashift:DI (match_dup 5) (const_int 3))
19390 (match_operand:DI 4 "register_operand" "1")))
19391 (set (mem:BLK (match_dup 3))
19392 (mem:BLK (match_dup 4)))
19393 (use (match_dup 5))]
19396 [(set_attr "type" "str")
19397 (set_attr "prefix_rep" "1")
19398 (set_attr "memory" "both")
19399 (set_attr "mode" "DI")])
19401 (define_insn "*rep_movsi"
19402 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
19403 (set (match_operand:SI 0 "register_operand" "=D")
19404 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
19406 (match_operand:SI 3 "register_operand" "0")))
19407 (set (match_operand:SI 1 "register_operand" "=S")
19408 (plus:SI (ashift:SI (match_dup 5) (const_int 2))
19409 (match_operand:SI 4 "register_operand" "1")))
19410 (set (mem:BLK (match_dup 3))
19411 (mem:BLK (match_dup 4)))
19412 (use (match_dup 5))]
19415 [(set_attr "type" "str")
19416 (set_attr "prefix_rep" "1")
19417 (set_attr "memory" "both")
19418 (set_attr "mode" "SI")])
19420 (define_insn "*rep_movsi_rex64"
19421 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
19422 (set (match_operand:DI 0 "register_operand" "=D")
19423 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
19425 (match_operand:DI 3 "register_operand" "0")))
19426 (set (match_operand:DI 1 "register_operand" "=S")
19427 (plus:DI (ashift:DI (match_dup 5) (const_int 2))
19428 (match_operand:DI 4 "register_operand" "1")))
19429 (set (mem:BLK (match_dup 3))
19430 (mem:BLK (match_dup 4)))
19431 (use (match_dup 5))]
19434 [(set_attr "type" "str")
19435 (set_attr "prefix_rep" "1")
19436 (set_attr "memory" "both")
19437 (set_attr "mode" "SI")])
19439 (define_insn "*rep_movqi"
19440 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
19441 (set (match_operand:SI 0 "register_operand" "=D")
19442 (plus:SI (match_operand:SI 3 "register_operand" "0")
19443 (match_operand:SI 5 "register_operand" "2")))
19444 (set (match_operand:SI 1 "register_operand" "=S")
19445 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
19446 (set (mem:BLK (match_dup 3))
19447 (mem:BLK (match_dup 4)))
19448 (use (match_dup 5))]
19451 [(set_attr "type" "str")
19452 (set_attr "prefix_rep" "1")
19453 (set_attr "memory" "both")
19454 (set_attr "mode" "SI")])
19456 (define_insn "*rep_movqi_rex64"
19457 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
19458 (set (match_operand:DI 0 "register_operand" "=D")
19459 (plus:DI (match_operand:DI 3 "register_operand" "0")
19460 (match_operand:DI 5 "register_operand" "2")))
19461 (set (match_operand:DI 1 "register_operand" "=S")
19462 (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
19463 (set (mem:BLK (match_dup 3))
19464 (mem:BLK (match_dup 4)))
19465 (use (match_dup 5))]
19468 [(set_attr "type" "str")
19469 (set_attr "prefix_rep" "1")
19470 (set_attr "memory" "both")
19471 (set_attr "mode" "SI")])
19473 (define_expand "setmemsi"
19474 [(use (match_operand:BLK 0 "memory_operand" ""))
19475 (use (match_operand:SI 1 "nonmemory_operand" ""))
19476 (use (match_operand 2 "const_int_operand" ""))
19477 (use (match_operand 3 "const_int_operand" ""))
19478 (use (match_operand:SI 4 "const_int_operand" ""))
19479 (use (match_operand:SI 5 "const_int_operand" ""))]
19482 if (ix86_expand_setmem (operands[0], operands[1],
19483 operands[2], operands[3],
19484 operands[4], operands[5]))
19490 (define_expand "setmemdi"
19491 [(use (match_operand:BLK 0 "memory_operand" ""))
19492 (use (match_operand:DI 1 "nonmemory_operand" ""))
19493 (use (match_operand 2 "const_int_operand" ""))
19494 (use (match_operand 3 "const_int_operand" ""))
19495 (use (match_operand 4 "const_int_operand" ""))
19496 (use (match_operand 5 "const_int_operand" ""))]
19499 if (ix86_expand_setmem (operands[0], operands[1],
19500 operands[2], operands[3],
19501 operands[4], operands[5]))
19507 ;; Most CPUs don't like single string operations
19508 ;; Handle this case here to simplify previous expander.
19510 (define_expand "strset"
19511 [(set (match_operand 1 "memory_operand" "")
19512 (match_operand 2 "register_operand" ""))
19513 (parallel [(set (match_operand 0 "register_operand" "")
19515 (clobber (reg:CC FLAGS_REG))])]
19518 if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
19519 operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
19521 /* If .md ever supports :P for Pmode, this can be directly
19522 in the pattern above. */
19523 operands[3] = gen_rtx_PLUS (Pmode, operands[0],
19524 GEN_INT (GET_MODE_SIZE (GET_MODE
19526 if (TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
19528 emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
19534 (define_expand "strset_singleop"
19535 [(parallel [(set (match_operand 1 "memory_operand" "")
19536 (match_operand 2 "register_operand" ""))
19537 (set (match_operand 0 "register_operand" "")
19538 (match_operand 3 "" ""))])]
19540 "ix86_current_function_needs_cld = 1;")
19542 (define_insn "*strsetdi_rex_1"
19543 [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
19544 (match_operand:DI 2 "register_operand" "a"))
19545 (set (match_operand:DI 0 "register_operand" "=D")
19546 (plus:DI (match_dup 1)
19550 [(set_attr "type" "str")
19551 (set_attr "memory" "store")
19552 (set_attr "mode" "DI")])
19554 (define_insn "*strsetsi_1"
19555 [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
19556 (match_operand:SI 2 "register_operand" "a"))
19557 (set (match_operand:SI 0 "register_operand" "=D")
19558 (plus:SI (match_dup 1)
19562 [(set_attr "type" "str")
19563 (set_attr "memory" "store")
19564 (set_attr "mode" "SI")])
19566 (define_insn "*strsetsi_rex_1"
19567 [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
19568 (match_operand:SI 2 "register_operand" "a"))
19569 (set (match_operand:DI 0 "register_operand" "=D")
19570 (plus:DI (match_dup 1)
19574 [(set_attr "type" "str")
19575 (set_attr "memory" "store")
19576 (set_attr "mode" "SI")])
19578 (define_insn "*strsethi_1"
19579 [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
19580 (match_operand:HI 2 "register_operand" "a"))
19581 (set (match_operand:SI 0 "register_operand" "=D")
19582 (plus:SI (match_dup 1)
19586 [(set_attr "type" "str")
19587 (set_attr "memory" "store")
19588 (set_attr "mode" "HI")])
19590 (define_insn "*strsethi_rex_1"
19591 [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
19592 (match_operand:HI 2 "register_operand" "a"))
19593 (set (match_operand:DI 0 "register_operand" "=D")
19594 (plus:DI (match_dup 1)
19598 [(set_attr "type" "str")
19599 (set_attr "memory" "store")
19600 (set_attr "mode" "HI")])
19602 (define_insn "*strsetqi_1"
19603 [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
19604 (match_operand:QI 2 "register_operand" "a"))
19605 (set (match_operand:SI 0 "register_operand" "=D")
19606 (plus:SI (match_dup 1)
19610 [(set_attr "type" "str")
19611 (set_attr "memory" "store")
19612 (set_attr "mode" "QI")])
19614 (define_insn "*strsetqi_rex_1"
19615 [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
19616 (match_operand:QI 2 "register_operand" "a"))
19617 (set (match_operand:DI 0 "register_operand" "=D")
19618 (plus:DI (match_dup 1)
19622 [(set_attr "type" "str")
19623 (set_attr "memory" "store")
19624 (set_attr "mode" "QI")])
19626 (define_expand "rep_stos"
19627 [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
19628 (set (match_operand 0 "register_operand" "")
19629 (match_operand 4 "" ""))
19630 (set (match_operand 2 "memory_operand" "") (const_int 0))
19631 (use (match_operand 3 "register_operand" ""))
19632 (use (match_dup 1))])]
19634 "ix86_current_function_needs_cld = 1;")
19636 (define_insn "*rep_stosdi_rex64"
19637 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
19638 (set (match_operand:DI 0 "register_operand" "=D")
19639 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
19641 (match_operand:DI 3 "register_operand" "0")))
19642 (set (mem:BLK (match_dup 3))
19644 (use (match_operand:DI 2 "register_operand" "a"))
19645 (use (match_dup 4))]
19648 [(set_attr "type" "str")
19649 (set_attr "prefix_rep" "1")
19650 (set_attr "memory" "store")
19651 (set_attr "mode" "DI")])
19653 (define_insn "*rep_stossi"
19654 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
19655 (set (match_operand:SI 0 "register_operand" "=D")
19656 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
19658 (match_operand:SI 3 "register_operand" "0")))
19659 (set (mem:BLK (match_dup 3))
19661 (use (match_operand:SI 2 "register_operand" "a"))
19662 (use (match_dup 4))]
19665 [(set_attr "type" "str")
19666 (set_attr "prefix_rep" "1")
19667 (set_attr "memory" "store")
19668 (set_attr "mode" "SI")])
19670 (define_insn "*rep_stossi_rex64"
19671 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
19672 (set (match_operand:DI 0 "register_operand" "=D")
19673 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
19675 (match_operand:DI 3 "register_operand" "0")))
19676 (set (mem:BLK (match_dup 3))
19678 (use (match_operand:SI 2 "register_operand" "a"))
19679 (use (match_dup 4))]
19682 [(set_attr "type" "str")
19683 (set_attr "prefix_rep" "1")
19684 (set_attr "memory" "store")
19685 (set_attr "mode" "SI")])
19687 (define_insn "*rep_stosqi"
19688 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
19689 (set (match_operand:SI 0 "register_operand" "=D")
19690 (plus:SI (match_operand:SI 3 "register_operand" "0")
19691 (match_operand:SI 4 "register_operand" "1")))
19692 (set (mem:BLK (match_dup 3))
19694 (use (match_operand:QI 2 "register_operand" "a"))
19695 (use (match_dup 4))]
19698 [(set_attr "type" "str")
19699 (set_attr "prefix_rep" "1")
19700 (set_attr "memory" "store")
19701 (set_attr "mode" "QI")])
19703 (define_insn "*rep_stosqi_rex64"
19704 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
19705 (set (match_operand:DI 0 "register_operand" "=D")
19706 (plus:DI (match_operand:DI 3 "register_operand" "0")
19707 (match_operand:DI 4 "register_operand" "1")))
19708 (set (mem:BLK (match_dup 3))
19710 (use (match_operand:QI 2 "register_operand" "a"))
19711 (use (match_dup 4))]
19714 [(set_attr "type" "str")
19715 (set_attr "prefix_rep" "1")
19716 (set_attr "memory" "store")
19717 (set_attr "mode" "QI")])
19719 (define_expand "cmpstrnsi"
19720 [(set (match_operand:SI 0 "register_operand" "")
19721 (compare:SI (match_operand:BLK 1 "general_operand" "")
19722 (match_operand:BLK 2 "general_operand" "")))
19723 (use (match_operand 3 "general_operand" ""))
19724 (use (match_operand 4 "immediate_operand" ""))]
19727 rtx addr1, addr2, out, outlow, count, countreg, align;
19729 if (optimize_insn_for_size_p () && !TARGET_INLINE_ALL_STRINGOPS)
19732 /* Can't use this if the user has appropriated esi or edi. */
19733 if (fixed_regs[SI_REG] || fixed_regs[DI_REG])
19738 out = gen_reg_rtx (SImode);
19740 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
19741 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
19742 if (addr1 != XEXP (operands[1], 0))
19743 operands[1] = replace_equiv_address_nv (operands[1], addr1);
19744 if (addr2 != XEXP (operands[2], 0))
19745 operands[2] = replace_equiv_address_nv (operands[2], addr2);
19747 count = operands[3];
19748 countreg = ix86_zero_extend_to_Pmode (count);
19750 /* %%% Iff we are testing strict equality, we can use known alignment
19751 to good advantage. This may be possible with combine, particularly
19752 once cc0 is dead. */
19753 align = operands[4];
19755 if (CONST_INT_P (count))
19757 if (INTVAL (count) == 0)
19759 emit_move_insn (operands[0], const0_rtx);
19762 emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
19763 operands[1], operands[2]));
19768 emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
19770 emit_insn (gen_cmpsi_1 (countreg, countreg));
19771 emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
19772 operands[1], operands[2]));
19775 outlow = gen_lowpart (QImode, out);
19776 emit_insn (gen_cmpintqi (outlow));
19777 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
19779 if (operands[0] != out)
19780 emit_move_insn (operands[0], out);
19785 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
19787 (define_expand "cmpintqi"
19788 [(set (match_dup 1)
19789 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19791 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19792 (parallel [(set (match_operand:QI 0 "register_operand" "")
19793 (minus:QI (match_dup 1)
19795 (clobber (reg:CC FLAGS_REG))])]
19797 "operands[1] = gen_reg_rtx (QImode);
19798 operands[2] = gen_reg_rtx (QImode);")
19800 ;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is
19801 ;; zero. Emit extra code to make sure that a zero-length compare is EQ.
19803 (define_expand "cmpstrnqi_nz_1"
19804 [(parallel [(set (reg:CC FLAGS_REG)
19805 (compare:CC (match_operand 4 "memory_operand" "")
19806 (match_operand 5 "memory_operand" "")))
19807 (use (match_operand 2 "register_operand" ""))
19808 (use (match_operand:SI 3 "immediate_operand" ""))
19809 (clobber (match_operand 0 "register_operand" ""))
19810 (clobber (match_operand 1 "register_operand" ""))
19811 (clobber (match_dup 2))])]
19813 "ix86_current_function_needs_cld = 1;")
19815 (define_insn "*cmpstrnqi_nz_1"
19816 [(set (reg:CC FLAGS_REG)
19817 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
19818 (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
19819 (use (match_operand:SI 6 "register_operand" "2"))
19820 (use (match_operand:SI 3 "immediate_operand" "i"))
19821 (clobber (match_operand:SI 0 "register_operand" "=S"))
19822 (clobber (match_operand:SI 1 "register_operand" "=D"))
19823 (clobber (match_operand:SI 2 "register_operand" "=c"))]
19826 [(set_attr "type" "str")
19827 (set_attr "mode" "QI")
19828 (set_attr "prefix_rep" "1")])
19830 (define_insn "*cmpstrnqi_nz_rex_1"
19831 [(set (reg:CC FLAGS_REG)
19832 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
19833 (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
19834 (use (match_operand:DI 6 "register_operand" "2"))
19835 (use (match_operand:SI 3 "immediate_operand" "i"))
19836 (clobber (match_operand:DI 0 "register_operand" "=S"))
19837 (clobber (match_operand:DI 1 "register_operand" "=D"))
19838 (clobber (match_operand:DI 2 "register_operand" "=c"))]
19841 [(set_attr "type" "str")
19842 (set_attr "mode" "QI")
19843 (set_attr "prefix_rep" "1")])
19845 ;; The same, but the count is not known to not be zero.
19847 (define_expand "cmpstrnqi_1"
19848 [(parallel [(set (reg:CC FLAGS_REG)
19849 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
19851 (compare:CC (match_operand 4 "memory_operand" "")
19852 (match_operand 5 "memory_operand" ""))
19854 (use (match_operand:SI 3 "immediate_operand" ""))
19855 (use (reg:CC FLAGS_REG))
19856 (clobber (match_operand 0 "register_operand" ""))
19857 (clobber (match_operand 1 "register_operand" ""))
19858 (clobber (match_dup 2))])]
19860 "ix86_current_function_needs_cld = 1;")
19862 (define_insn "*cmpstrnqi_1"
19863 [(set (reg:CC FLAGS_REG)
19864 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
19866 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
19867 (mem:BLK (match_operand:SI 5 "register_operand" "1")))
19869 (use (match_operand:SI 3 "immediate_operand" "i"))
19870 (use (reg:CC FLAGS_REG))
19871 (clobber (match_operand:SI 0 "register_operand" "=S"))
19872 (clobber (match_operand:SI 1 "register_operand" "=D"))
19873 (clobber (match_operand:SI 2 "register_operand" "=c"))]
19876 [(set_attr "type" "str")
19877 (set_attr "mode" "QI")
19878 (set_attr "prefix_rep" "1")])
19880 (define_insn "*cmpstrnqi_rex_1"
19881 [(set (reg:CC FLAGS_REG)
19882 (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
19884 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
19885 (mem:BLK (match_operand:DI 5 "register_operand" "1")))
19887 (use (match_operand:SI 3 "immediate_operand" "i"))
19888 (use (reg:CC FLAGS_REG))
19889 (clobber (match_operand:DI 0 "register_operand" "=S"))
19890 (clobber (match_operand:DI 1 "register_operand" "=D"))
19891 (clobber (match_operand:DI 2 "register_operand" "=c"))]
19894 [(set_attr "type" "str")
19895 (set_attr "mode" "QI")
19896 (set_attr "prefix_rep" "1")])
19898 (define_expand "strlensi"
19899 [(set (match_operand:SI 0 "register_operand" "")
19900 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
19901 (match_operand:QI 2 "immediate_operand" "")
19902 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19905 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19911 (define_expand "strlendi"
19912 [(set (match_operand:DI 0 "register_operand" "")
19913 (unspec:DI [(match_operand:BLK 1 "general_operand" "")
19914 (match_operand:QI 2 "immediate_operand" "")
19915 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19918 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19924 (define_expand "strlenqi_1"
19925 [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
19926 (clobber (match_operand 1 "register_operand" ""))
19927 (clobber (reg:CC FLAGS_REG))])]
19929 "ix86_current_function_needs_cld = 1;")
19931 (define_insn "*strlenqi_1"
19932 [(set (match_operand:SI 0 "register_operand" "=&c")
19933 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
19934 (match_operand:QI 2 "register_operand" "a")
19935 (match_operand:SI 3 "immediate_operand" "i")
19936 (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
19937 (clobber (match_operand:SI 1 "register_operand" "=D"))
19938 (clobber (reg:CC FLAGS_REG))]
19941 [(set_attr "type" "str")
19942 (set_attr "mode" "QI")
19943 (set_attr "prefix_rep" "1")])
19945 (define_insn "*strlenqi_rex_1"
19946 [(set (match_operand:DI 0 "register_operand" "=&c")
19947 (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
19948 (match_operand:QI 2 "register_operand" "a")
19949 (match_operand:DI 3 "immediate_operand" "i")
19950 (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
19951 (clobber (match_operand:DI 1 "register_operand" "=D"))
19952 (clobber (reg:CC FLAGS_REG))]
19955 [(set_attr "type" "str")
19956 (set_attr "mode" "QI")
19957 (set_attr "prefix_rep" "1")])
19959 ;; Peephole optimizations to clean up after cmpstrn*. This should be
19960 ;; handled in combine, but it is not currently up to the task.
19961 ;; When used for their truth value, the cmpstrn* expanders generate
19970 ;; The intermediate three instructions are unnecessary.
19972 ;; This one handles cmpstrn*_nz_1...
19975 (set (reg:CC FLAGS_REG)
19976 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
19977 (mem:BLK (match_operand 5 "register_operand" ""))))
19978 (use (match_operand 6 "register_operand" ""))
19979 (use (match_operand:SI 3 "immediate_operand" ""))
19980 (clobber (match_operand 0 "register_operand" ""))
19981 (clobber (match_operand 1 "register_operand" ""))
19982 (clobber (match_operand 2 "register_operand" ""))])
19983 (set (match_operand:QI 7 "register_operand" "")
19984 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19985 (set (match_operand:QI 8 "register_operand" "")
19986 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19987 (set (reg FLAGS_REG)
19988 (compare (match_dup 7) (match_dup 8)))
19990 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
19992 (set (reg:CC FLAGS_REG)
19993 (compare:CC (mem:BLK (match_dup 4))
19994 (mem:BLK (match_dup 5))))
19995 (use (match_dup 6))
19996 (use (match_dup 3))
19997 (clobber (match_dup 0))
19998 (clobber (match_dup 1))
19999 (clobber (match_dup 2))])]
20002 ;; ...and this one handles cmpstrn*_1.
20005 (set (reg:CC FLAGS_REG)
20006 (if_then_else:CC (ne (match_operand 6 "register_operand" "")
20008 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
20009 (mem:BLK (match_operand 5 "register_operand" "")))
20011 (use (match_operand:SI 3 "immediate_operand" ""))
20012 (use (reg:CC FLAGS_REG))
20013 (clobber (match_operand 0 "register_operand" ""))
20014 (clobber (match_operand 1 "register_operand" ""))
20015 (clobber (match_operand 2 "register_operand" ""))])
20016 (set (match_operand:QI 7 "register_operand" "")
20017 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
20018 (set (match_operand:QI 8 "register_operand" "")
20019 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
20020 (set (reg FLAGS_REG)
20021 (compare (match_dup 7) (match_dup 8)))
20023 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
20025 (set (reg:CC FLAGS_REG)
20026 (if_then_else:CC (ne (match_dup 6)
20028 (compare:CC (mem:BLK (match_dup 4))
20029 (mem:BLK (match_dup 5)))
20031 (use (match_dup 3))
20032 (use (reg:CC FLAGS_REG))
20033 (clobber (match_dup 0))
20034 (clobber (match_dup 1))
20035 (clobber (match_dup 2))])]
20040 ;; Conditional move instructions.
20042 (define_expand "movdicc"
20043 [(set (match_operand:DI 0 "register_operand" "")
20044 (if_then_else:DI (match_operand 1 "comparison_operator" "")
20045 (match_operand:DI 2 "general_operand" "")
20046 (match_operand:DI 3 "general_operand" "")))]
20048 "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
20050 (define_insn "x86_movdicc_0_m1_rex64"
20051 [(set (match_operand:DI 0 "register_operand" "=r")
20052 (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
20055 (clobber (reg:CC FLAGS_REG))]
20058 ; Since we don't have the proper number of operands for an alu insn,
20059 ; fill in all the blanks.
20060 [(set_attr "type" "alu")
20061 (set_attr "use_carry" "1")
20062 (set_attr "pent_pair" "pu")
20063 (set_attr "memory" "none")
20064 (set_attr "imm_disp" "false")
20065 (set_attr "mode" "DI")
20066 (set_attr "length_immediate" "0")])
20068 (define_insn "*x86_movdicc_0_m1_se"
20069 [(set (match_operand:DI 0 "register_operand" "=r")
20070 (sign_extract:DI (match_operand 1 "ix86_carry_flag_operator" "")
20073 (clobber (reg:CC FLAGS_REG))]
20076 [(set_attr "type" "alu")
20077 (set_attr "use_carry" "1")
20078 (set_attr "pent_pair" "pu")
20079 (set_attr "memory" "none")
20080 (set_attr "imm_disp" "false")
20081 (set_attr "mode" "DI")
20082 (set_attr "length_immediate" "0")])
20084 (define_insn "*movdicc_c_rex64"
20085 [(set (match_operand:DI 0 "register_operand" "=r,r")
20086 (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
20087 [(reg FLAGS_REG) (const_int 0)])
20088 (match_operand:DI 2 "nonimmediate_operand" "rm,0")
20089 (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
20090 "TARGET_64BIT && TARGET_CMOVE
20091 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20093 cmov%O2%C1\t{%2, %0|%0, %2}
20094 cmov%O2%c1\t{%3, %0|%0, %3}"
20095 [(set_attr "type" "icmov")
20096 (set_attr "mode" "DI")])
20098 (define_expand "movsicc"
20099 [(set (match_operand:SI 0 "register_operand" "")
20100 (if_then_else:SI (match_operand 1 "comparison_operator" "")
20101 (match_operand:SI 2 "general_operand" "")
20102 (match_operand:SI 3 "general_operand" "")))]
20104 "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
20106 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
20107 ;; the register first winds up with `sbbl $0,reg', which is also weird.
20108 ;; So just document what we're doing explicitly.
20110 (define_insn "x86_movsicc_0_m1"
20111 [(set (match_operand:SI 0 "register_operand" "=r")
20112 (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
20115 (clobber (reg:CC FLAGS_REG))]
20118 ; Since we don't have the proper number of operands for an alu insn,
20119 ; fill in all the blanks.
20120 [(set_attr "type" "alu")
20121 (set_attr "use_carry" "1")
20122 (set_attr "pent_pair" "pu")
20123 (set_attr "memory" "none")
20124 (set_attr "imm_disp" "false")
20125 (set_attr "mode" "SI")
20126 (set_attr "length_immediate" "0")])
20128 (define_insn "*x86_movsicc_0_m1_se"
20129 [(set (match_operand:SI 0 "register_operand" "=r")
20130 (sign_extract:SI (match_operand 1 "ix86_carry_flag_operator" "")
20133 (clobber (reg:CC FLAGS_REG))]
20136 [(set_attr "type" "alu")
20137 (set_attr "use_carry" "1")
20138 (set_attr "pent_pair" "pu")
20139 (set_attr "memory" "none")
20140 (set_attr "imm_disp" "false")
20141 (set_attr "mode" "SI")
20142 (set_attr "length_immediate" "0")])
20144 (define_insn "*movsicc_noc"
20145 [(set (match_operand:SI 0 "register_operand" "=r,r")
20146 (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
20147 [(reg FLAGS_REG) (const_int 0)])
20148 (match_operand:SI 2 "nonimmediate_operand" "rm,0")
20149 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
20151 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20153 cmov%O2%C1\t{%2, %0|%0, %2}
20154 cmov%O2%c1\t{%3, %0|%0, %3}"
20155 [(set_attr "type" "icmov")
20156 (set_attr "mode" "SI")])
20158 (define_expand "movhicc"
20159 [(set (match_operand:HI 0 "register_operand" "")
20160 (if_then_else:HI (match_operand 1 "comparison_operator" "")
20161 (match_operand:HI 2 "general_operand" "")
20162 (match_operand:HI 3 "general_operand" "")))]
20163 "TARGET_HIMODE_MATH"
20164 "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
20166 (define_insn "*movhicc_noc"
20167 [(set (match_operand:HI 0 "register_operand" "=r,r")
20168 (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
20169 [(reg FLAGS_REG) (const_int 0)])
20170 (match_operand:HI 2 "nonimmediate_operand" "rm,0")
20171 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
20173 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20175 cmov%O2%C1\t{%2, %0|%0, %2}
20176 cmov%O2%c1\t{%3, %0|%0, %3}"
20177 [(set_attr "type" "icmov")
20178 (set_attr "mode" "HI")])
20180 (define_expand "movqicc"
20181 [(set (match_operand:QI 0 "register_operand" "")
20182 (if_then_else:QI (match_operand 1 "comparison_operator" "")
20183 (match_operand:QI 2 "general_operand" "")
20184 (match_operand:QI 3 "general_operand" "")))]
20185 "TARGET_QIMODE_MATH"
20186 "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
20188 (define_insn_and_split "*movqicc_noc"
20189 [(set (match_operand:QI 0 "register_operand" "=r,r")
20190 (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
20191 [(match_operand 4 "flags_reg_operand" "")
20193 (match_operand:QI 2 "register_operand" "r,0")
20194 (match_operand:QI 3 "register_operand" "0,r")))]
20195 "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
20197 "&& reload_completed"
20198 [(set (match_dup 0)
20199 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
20202 "operands[0] = gen_lowpart (SImode, operands[0]);
20203 operands[2] = gen_lowpart (SImode, operands[2]);
20204 operands[3] = gen_lowpart (SImode, operands[3]);"
20205 [(set_attr "type" "icmov")
20206 (set_attr "mode" "SI")])
20208 (define_expand "mov<mode>cc"
20209 [(set (match_operand:X87MODEF 0 "register_operand" "")
20210 (if_then_else:X87MODEF
20211 (match_operand 1 "comparison_operator" "")
20212 (match_operand:X87MODEF 2 "register_operand" "")
20213 (match_operand:X87MODEF 3 "register_operand" "")))]
20214 "(TARGET_80387 && TARGET_CMOVE)
20215 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
20216 "if (ix86_expand_fp_movcc (operands)) DONE; else FAIL;")
20218 (define_insn "*movsfcc_1_387"
20219 [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
20220 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
20221 [(reg FLAGS_REG) (const_int 0)])
20222 (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
20223 (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
20224 "TARGET_80387 && TARGET_CMOVE
20225 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20227 fcmov%F1\t{%2, %0|%0, %2}
20228 fcmov%f1\t{%3, %0|%0, %3}
20229 cmov%O2%C1\t{%2, %0|%0, %2}
20230 cmov%O2%c1\t{%3, %0|%0, %3}"
20231 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
20232 (set_attr "mode" "SF,SF,SI,SI")])
20234 (define_insn "*movdfcc_1"
20235 [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
20236 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
20237 [(reg FLAGS_REG) (const_int 0)])
20238 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
20239 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
20240 "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
20241 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20243 fcmov%F1\t{%2, %0|%0, %2}
20244 fcmov%f1\t{%3, %0|%0, %3}
20247 [(set_attr "type" "fcmov,fcmov,multi,multi")
20248 (set_attr "mode" "DF")])
20250 (define_insn "*movdfcc_1_rex64"
20251 [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
20252 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
20253 [(reg FLAGS_REG) (const_int 0)])
20254 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
20255 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
20256 "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
20257 && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
20259 fcmov%F1\t{%2, %0|%0, %2}
20260 fcmov%f1\t{%3, %0|%0, %3}
20261 cmov%O2%C1\t{%2, %0|%0, %2}
20262 cmov%O2%c1\t{%3, %0|%0, %3}"
20263 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
20264 (set_attr "mode" "DF")])
20267 [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
20268 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
20269 [(match_operand 4 "flags_reg_operand" "")
20271 (match_operand:DF 2 "nonimmediate_operand" "")
20272 (match_operand:DF 3 "nonimmediate_operand" "")))]
20273 "!TARGET_64BIT && reload_completed"
20274 [(set (match_dup 2)
20275 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
20279 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
20282 "split_di (&operands[2], 2, &operands[5], &operands[7]);
20283 split_di (&operands[0], 1, &operands[2], &operands[3]);")
20285 (define_insn "*movxfcc_1"
20286 [(set (match_operand:XF 0 "register_operand" "=f,f")
20287 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
20288 [(reg FLAGS_REG) (const_int 0)])
20289 (match_operand:XF 2 "register_operand" "f,0")
20290 (match_operand:XF 3 "register_operand" "0,f")))]
20291 "TARGET_80387 && TARGET_CMOVE"
20293 fcmov%F1\t{%2, %0|%0, %2}
20294 fcmov%f1\t{%3, %0|%0, %3}"
20295 [(set_attr "type" "fcmov")
20296 (set_attr "mode" "XF")])
20298 ;; All moves in SSE5 pcmov instructions are 128 bits and hence we restrict
20299 ;; the scalar versions to have only XMM registers as operands.
20301 ;; SSE5 conditional move
20302 (define_insn "*sse5_pcmov_<mode>"
20303 [(set (match_operand:MODEF 0 "register_operand" "=x,x")
20304 (if_then_else:MODEF
20305 (match_operand:MODEF 1 "register_operand" "x,0")
20306 (match_operand:MODEF 2 "register_operand" "0,x")
20307 (match_operand:MODEF 3 "register_operand" "x,x")))]
20308 "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1, false)"
20309 "pcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
20310 [(set_attr "type" "sse4arg")])
20312 ;; These versions of the min/max patterns are intentionally ignorant of
20313 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
20314 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
20315 ;; are undefined in this condition, we're certain this is correct.
20317 (define_insn "*avx_<code><mode>3"
20318 [(set (match_operand:MODEF 0 "register_operand" "=x")
20320 (match_operand:MODEF 1 "nonimmediate_operand" "%x")
20321 (match_operand:MODEF 2 "nonimmediate_operand" "xm")))]
20322 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20323 "v<maxminfprefix>s<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
20324 [(set_attr "type" "sseadd")
20325 (set_attr "prefix" "vex")
20326 (set_attr "mode" "<MODE>")])
20328 (define_insn "<code><mode>3"
20329 [(set (match_operand:MODEF 0 "register_operand" "=x")
20331 (match_operand:MODEF 1 "nonimmediate_operand" "%0")
20332 (match_operand:MODEF 2 "nonimmediate_operand" "xm")))]
20333 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20334 "<maxminfprefix>s<ssemodefsuffix>\t{%2, %0|%0, %2}"
20335 [(set_attr "type" "sseadd")
20336 (set_attr "mode" "<MODE>")])
20338 ;; These versions of the min/max patterns implement exactly the operations
20339 ;; min = (op1 < op2 ? op1 : op2)
20340 ;; max = (!(op1 < op2) ? op1 : op2)
20341 ;; Their operands are not commutative, and thus they may be used in the
20342 ;; presence of -0.0 and NaN.
20344 (define_insn "*avx_ieee_smin<mode>3"
20345 [(set (match_operand:MODEF 0 "register_operand" "=x")
20347 [(match_operand:MODEF 1 "register_operand" "x")
20348 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
20350 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20351 "vmins<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
20352 [(set_attr "type" "sseadd")
20353 (set_attr "prefix" "vex")
20354 (set_attr "mode" "<MODE>")])
20356 (define_insn "*ieee_smin<mode>3"
20357 [(set (match_operand:MODEF 0 "register_operand" "=x")
20359 [(match_operand:MODEF 1 "register_operand" "0")
20360 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
20362 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20363 "mins<ssemodefsuffix>\t{%2, %0|%0, %2}"
20364 [(set_attr "type" "sseadd")
20365 (set_attr "mode" "<MODE>")])
20367 (define_insn "*avx_ieee_smax<mode>3"
20368 [(set (match_operand:MODEF 0 "register_operand" "=x")
20370 [(match_operand:MODEF 1 "register_operand" "0")
20371 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
20373 "AVX_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20374 "vmaxs<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
20375 [(set_attr "type" "sseadd")
20376 (set_attr "prefix" "vex")
20377 (set_attr "mode" "<MODE>")])
20379 (define_insn "*ieee_smax<mode>3"
20380 [(set (match_operand:MODEF 0 "register_operand" "=x")
20382 [(match_operand:MODEF 1 "register_operand" "0")
20383 (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
20385 "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
20386 "maxs<ssemodefsuffix>\t{%2, %0|%0, %2}"
20387 [(set_attr "type" "sseadd")
20388 (set_attr "mode" "<MODE>")])
20390 ;; Make two stack loads independent:
20392 ;; fld %st(0) -> fld bb
20393 ;; fmul bb fmul %st(1), %st
20395 ;; Actually we only match the last two instructions for simplicity.
20397 [(set (match_operand 0 "fp_register_operand" "")
20398 (match_operand 1 "fp_register_operand" ""))
20400 (match_operator 2 "binary_fp_operator"
20402 (match_operand 3 "memory_operand" "")]))]
20403 "REGNO (operands[0]) != REGNO (operands[1])"
20404 [(set (match_dup 0) (match_dup 3))
20405 (set (match_dup 0) (match_dup 4))]
20407 ;; The % modifier is not operational anymore in peephole2's, so we have to
20408 ;; swap the operands manually in the case of addition and multiplication.
20409 "if (COMMUTATIVE_ARITH_P (operands[2]))
20410 operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
20411 operands[0], operands[1]);
20413 operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
20414 operands[1], operands[0]);")
20416 ;; Conditional addition patterns
20417 (define_expand "add<mode>cc"
20418 [(match_operand:SWI 0 "register_operand" "")
20419 (match_operand 1 "comparison_operator" "")
20420 (match_operand:SWI 2 "register_operand" "")
20421 (match_operand:SWI 3 "const_int_operand" "")]
20423 "if (ix86_expand_int_addcc (operands)) DONE; else FAIL;")
20426 ;; Misc patterns (?)
20428 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
20429 ;; Otherwise there will be nothing to keep
20431 ;; [(set (reg ebp) (reg esp))]
20432 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
20433 ;; (clobber (eflags)]
20434 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
20436 ;; in proper program order.
20437 (define_insn "pro_epilogue_adjust_stack_1"
20438 [(set (match_operand:SI 0 "register_operand" "=r,r")
20439 (plus:SI (match_operand:SI 1 "register_operand" "0,r")
20440 (match_operand:SI 2 "immediate_operand" "i,i")))
20441 (clobber (reg:CC FLAGS_REG))
20442 (clobber (mem:BLK (scratch)))]
20445 switch (get_attr_type (insn))
20448 return "mov{l}\t{%1, %0|%0, %1}";
20451 if (CONST_INT_P (operands[2])
20452 && (INTVAL (operands[2]) == 128
20453 || (INTVAL (operands[2]) < 0
20454 && INTVAL (operands[2]) != -128)))
20456 operands[2] = GEN_INT (-INTVAL (operands[2]));
20457 return "sub{l}\t{%2, %0|%0, %2}";
20459 return "add{l}\t{%2, %0|%0, %2}";
20462 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
20463 return "lea{l}\t{%a2, %0|%0, %a2}";
20466 gcc_unreachable ();
20469 [(set (attr "type")
20470 (cond [(and (eq_attr "alternative" "0")
20471 (eq (symbol_ref "TARGET_OPT_AGU") (const_int 0)))
20472 (const_string "alu")
20473 (match_operand:SI 2 "const0_operand" "")
20474 (const_string "imov")
20476 (const_string "lea")))
20477 (set_attr "mode" "SI")])
20479 (define_insn "pro_epilogue_adjust_stack_rex64"
20480 [(set (match_operand:DI 0 "register_operand" "=r,r")
20481 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
20482 (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
20483 (clobber (reg:CC FLAGS_REG))
20484 (clobber (mem:BLK (scratch)))]
20487 switch (get_attr_type (insn))
20490 return "mov{q}\t{%1, %0|%0, %1}";
20493 if (CONST_INT_P (operands[2])
20494 /* Avoid overflows. */
20495 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
20496 && (INTVAL (operands[2]) == 128
20497 || (INTVAL (operands[2]) < 0
20498 && INTVAL (operands[2]) != -128)))
20500 operands[2] = GEN_INT (-INTVAL (operands[2]));
20501 return "sub{q}\t{%2, %0|%0, %2}";
20503 return "add{q}\t{%2, %0|%0, %2}";
20506 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
20507 return "lea{q}\t{%a2, %0|%0, %a2}";
20510 gcc_unreachable ();
20513 [(set (attr "type")
20514 (cond [(and (eq_attr "alternative" "0")
20515 (eq (symbol_ref "TARGET_OPT_AGU") (const_int 0)))
20516 (const_string "alu")
20517 (match_operand:DI 2 "const0_operand" "")
20518 (const_string "imov")
20520 (const_string "lea")))
20521 (set_attr "mode" "DI")])
20523 (define_insn "pro_epilogue_adjust_stack_rex64_2"
20524 [(set (match_operand:DI 0 "register_operand" "=r,r")
20525 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
20526 (match_operand:DI 3 "immediate_operand" "i,i")))
20527 (use (match_operand:DI 2 "register_operand" "r,r"))
20528 (clobber (reg:CC FLAGS_REG))
20529 (clobber (mem:BLK (scratch)))]
20532 switch (get_attr_type (insn))
20535 return "add{q}\t{%2, %0|%0, %2}";
20538 operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
20539 return "lea{q}\t{%a2, %0|%0, %a2}";
20542 gcc_unreachable ();
20545 [(set_attr "type" "alu,lea")
20546 (set_attr "mode" "DI")])
20548 (define_insn "allocate_stack_worker_32"
20549 [(set (match_operand:SI 0 "register_operand" "=a")
20550 (unspec_volatile:SI [(match_operand:SI 1 "register_operand" "0")]
20551 UNSPECV_STACK_PROBE))
20552 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 1)))
20553 (clobber (reg:CC FLAGS_REG))]
20554 "!TARGET_64BIT && TARGET_STACK_PROBE"
20556 [(set_attr "type" "multi")
20557 (set_attr "length" "5")])
20559 (define_insn "allocate_stack_worker_64"
20560 [(set (match_operand:DI 0 "register_operand" "=a")
20561 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "0")]
20562 UNSPECV_STACK_PROBE))
20563 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 1)))
20564 (clobber (reg:DI R10_REG))
20565 (clobber (reg:DI R11_REG))
20566 (clobber (reg:CC FLAGS_REG))]
20567 "TARGET_64BIT && TARGET_STACK_PROBE"
20569 [(set_attr "type" "multi")
20570 (set_attr "length" "5")])
20572 (define_expand "allocate_stack"
20573 [(match_operand 0 "register_operand" "")
20574 (match_operand 1 "general_operand" "")]
20575 "TARGET_STACK_PROBE"
20579 #ifndef CHECK_STACK_LIMIT
20580 #define CHECK_STACK_LIMIT 0
20583 if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
20584 && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
20586 x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
20587 stack_pointer_rtx, 0, OPTAB_DIRECT);
20588 if (x != stack_pointer_rtx)
20589 emit_move_insn (stack_pointer_rtx, x);
20593 x = copy_to_mode_reg (Pmode, operands[1]);
20595 x = gen_allocate_stack_worker_64 (x, x);
20597 x = gen_allocate_stack_worker_32 (x, x);
20601 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
20605 (define_expand "builtin_setjmp_receiver"
20606 [(label_ref (match_operand 0 "" ""))]
20607 "!TARGET_64BIT && flag_pic"
20613 rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
20614 rtx label_rtx = gen_label_rtx ();
20615 emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
20616 xops[0] = xops[1] = picreg;
20617 xops[2] = machopic_gen_offset (gen_rtx_LABEL_REF (SImode, label_rtx));
20618 ix86_expand_binary_operator (MINUS, SImode, xops);
20622 emit_insn (gen_set_got (pic_offset_table_rtx));
20626 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
20629 [(set (match_operand 0 "register_operand" "")
20630 (match_operator 3 "promotable_binary_operator"
20631 [(match_operand 1 "register_operand" "")
20632 (match_operand 2 "aligned_operand" "")]))
20633 (clobber (reg:CC FLAGS_REG))]
20634 "! TARGET_PARTIAL_REG_STALL && reload_completed
20635 && ((GET_MODE (operands[0]) == HImode
20636 && ((optimize_function_for_speed_p (cfun) && !TARGET_FAST_PREFIX)
20637 /* ??? next two lines just !satisfies_constraint_K (...) */
20638 || !CONST_INT_P (operands[2])
20639 || satisfies_constraint_K (operands[2])))
20640 || (GET_MODE (operands[0]) == QImode
20641 && (TARGET_PROMOTE_QImode || optimize_function_for_size_p (cfun))))"
20642 [(parallel [(set (match_dup 0)
20643 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
20644 (clobber (reg:CC FLAGS_REG))])]
20645 "operands[0] = gen_lowpart (SImode, operands[0]);
20646 operands[1] = gen_lowpart (SImode, operands[1]);
20647 if (GET_CODE (operands[3]) != ASHIFT)
20648 operands[2] = gen_lowpart (SImode, operands[2]);
20649 PUT_MODE (operands[3], SImode);")
20651 ; Promote the QImode tests, as i386 has encoding of the AND
20652 ; instruction with 32-bit sign-extended immediate and thus the
20653 ; instruction size is unchanged, except in the %eax case for
20654 ; which it is increased by one byte, hence the ! optimize_size.
20656 [(set (match_operand 0 "flags_reg_operand" "")
20657 (match_operator 2 "compare_operator"
20658 [(and (match_operand 3 "aligned_operand" "")
20659 (match_operand 4 "const_int_operand" ""))
20661 (set (match_operand 1 "register_operand" "")
20662 (and (match_dup 3) (match_dup 4)))]
20663 "! TARGET_PARTIAL_REG_STALL && reload_completed
20664 && optimize_insn_for_speed_p ()
20665 && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
20666 || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
20667 /* Ensure that the operand will remain sign-extended immediate. */
20668 && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
20669 [(parallel [(set (match_dup 0)
20670 (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
20673 (and:SI (match_dup 3) (match_dup 4)))])]
20676 = gen_int_mode (INTVAL (operands[4])
20677 & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
20678 operands[1] = gen_lowpart (SImode, operands[1]);
20679 operands[3] = gen_lowpart (SImode, operands[3]);
20682 ; Don't promote the QImode tests, as i386 doesn't have encoding of
20683 ; the TEST instruction with 32-bit sign-extended immediate and thus
20684 ; the instruction size would at least double, which is not what we
20685 ; want even with ! optimize_size.
20687 [(set (match_operand 0 "flags_reg_operand" "")
20688 (match_operator 1 "compare_operator"
20689 [(and (match_operand:HI 2 "aligned_operand" "")
20690 (match_operand:HI 3 "const_int_operand" ""))
20692 "! TARGET_PARTIAL_REG_STALL && reload_completed
20693 && ! TARGET_FAST_PREFIX
20694 && optimize_insn_for_speed_p ()
20695 /* Ensure that the operand will remain sign-extended immediate. */
20696 && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
20697 [(set (match_dup 0)
20698 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
20702 = gen_int_mode (INTVAL (operands[3])
20703 & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
20704 operands[2] = gen_lowpart (SImode, operands[2]);
20708 [(set (match_operand 0 "register_operand" "")
20709 (neg (match_operand 1 "register_operand" "")))
20710 (clobber (reg:CC FLAGS_REG))]
20711 "! TARGET_PARTIAL_REG_STALL && reload_completed
20712 && (GET_MODE (operands[0]) == HImode
20713 || (GET_MODE (operands[0]) == QImode
20714 && (TARGET_PROMOTE_QImode
20715 || optimize_insn_for_size_p ())))"
20716 [(parallel [(set (match_dup 0)
20717 (neg:SI (match_dup 1)))
20718 (clobber (reg:CC FLAGS_REG))])]
20719 "operands[0] = gen_lowpart (SImode, operands[0]);
20720 operands[1] = gen_lowpart (SImode, operands[1]);")
20723 [(set (match_operand 0 "register_operand" "")
20724 (not (match_operand 1 "register_operand" "")))]
20725 "! TARGET_PARTIAL_REG_STALL && reload_completed
20726 && (GET_MODE (operands[0]) == HImode
20727 || (GET_MODE (operands[0]) == QImode
20728 && (TARGET_PROMOTE_QImode
20729 || optimize_insn_for_size_p ())))"
20730 [(set (match_dup 0)
20731 (not:SI (match_dup 1)))]
20732 "operands[0] = gen_lowpart (SImode, operands[0]);
20733 operands[1] = gen_lowpart (SImode, operands[1]);")
20736 [(set (match_operand 0 "register_operand" "")
20737 (if_then_else (match_operator 1 "comparison_operator"
20738 [(reg FLAGS_REG) (const_int 0)])
20739 (match_operand 2 "register_operand" "")
20740 (match_operand 3 "register_operand" "")))]
20741 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
20742 && (GET_MODE (operands[0]) == HImode
20743 || (GET_MODE (operands[0]) == QImode
20744 && (TARGET_PROMOTE_QImode
20745 || optimize_insn_for_size_p ())))"
20746 [(set (match_dup 0)
20747 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
20748 "operands[0] = gen_lowpart (SImode, operands[0]);
20749 operands[2] = gen_lowpart (SImode, operands[2]);
20750 operands[3] = gen_lowpart (SImode, operands[3]);")
20753 ;; RTL Peephole optimizations, run before sched2. These primarily look to
20754 ;; transform a complex memory operation into two memory to register operations.
20756 ;; Don't push memory operands
20758 [(set (match_operand:SI 0 "push_operand" "")
20759 (match_operand:SI 1 "memory_operand" ""))
20760 (match_scratch:SI 2 "r")]
20761 "optimize_insn_for_speed_p () && !TARGET_PUSH_MEMORY
20762 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20763 [(set (match_dup 2) (match_dup 1))
20764 (set (match_dup 0) (match_dup 2))]
20768 [(set (match_operand:DI 0 "push_operand" "")
20769 (match_operand:DI 1 "memory_operand" ""))
20770 (match_scratch:DI 2 "r")]
20771 "optimize_insn_for_speed_p () && !TARGET_PUSH_MEMORY
20772 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20773 [(set (match_dup 2) (match_dup 1))
20774 (set (match_dup 0) (match_dup 2))]
20777 ;; We need to handle SFmode only, because DFmode and XFmode is split to
20780 [(set (match_operand:SF 0 "push_operand" "")
20781 (match_operand:SF 1 "memory_operand" ""))
20782 (match_scratch:SF 2 "r")]
20783 "optimize_insn_for_speed_p () && !TARGET_PUSH_MEMORY
20784 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20785 [(set (match_dup 2) (match_dup 1))
20786 (set (match_dup 0) (match_dup 2))]
20790 [(set (match_operand:HI 0 "push_operand" "")
20791 (match_operand:HI 1 "memory_operand" ""))
20792 (match_scratch:HI 2 "r")]
20793 "optimize_insn_for_speed_p () && !TARGET_PUSH_MEMORY
20794 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20795 [(set (match_dup 2) (match_dup 1))
20796 (set (match_dup 0) (match_dup 2))]
20800 [(set (match_operand:QI 0 "push_operand" "")
20801 (match_operand:QI 1 "memory_operand" ""))
20802 (match_scratch:QI 2 "q")]
20803 "optimize_insn_for_speed_p () && !TARGET_PUSH_MEMORY
20804 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20805 [(set (match_dup 2) (match_dup 1))
20806 (set (match_dup 0) (match_dup 2))]
20809 ;; Don't move an immediate directly to memory when the instruction
20812 [(match_scratch:SI 1 "r")
20813 (set (match_operand:SI 0 "memory_operand" "")
20815 "optimize_insn_for_speed_p ()
20816 && ! TARGET_USE_MOV0
20817 && TARGET_SPLIT_LONG_MOVES
20818 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
20819 && peep2_regno_dead_p (0, FLAGS_REG)"
20820 [(parallel [(set (match_dup 1) (const_int 0))
20821 (clobber (reg:CC FLAGS_REG))])
20822 (set (match_dup 0) (match_dup 1))]
20826 [(match_scratch:HI 1 "r")
20827 (set (match_operand:HI 0 "memory_operand" "")
20829 "optimize_insn_for_speed_p ()
20830 && ! TARGET_USE_MOV0
20831 && TARGET_SPLIT_LONG_MOVES
20832 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
20833 && peep2_regno_dead_p (0, FLAGS_REG)"
20834 [(parallel [(set (match_dup 2) (const_int 0))
20835 (clobber (reg:CC FLAGS_REG))])
20836 (set (match_dup 0) (match_dup 1))]
20837 "operands[2] = gen_lowpart (SImode, operands[1]);")
20840 [(match_scratch:QI 1 "q")
20841 (set (match_operand:QI 0 "memory_operand" "")
20843 "optimize_insn_for_speed_p ()
20844 && ! TARGET_USE_MOV0
20845 && TARGET_SPLIT_LONG_MOVES
20846 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
20847 && peep2_regno_dead_p (0, FLAGS_REG)"
20848 [(parallel [(set (match_dup 2) (const_int 0))
20849 (clobber (reg:CC FLAGS_REG))])
20850 (set (match_dup 0) (match_dup 1))]
20851 "operands[2] = gen_lowpart (SImode, operands[1]);")
20854 [(match_scratch:SI 2 "r")
20855 (set (match_operand:SI 0 "memory_operand" "")
20856 (match_operand:SI 1 "immediate_operand" ""))]
20857 "optimize_insn_for_speed_p ()
20858 && TARGET_SPLIT_LONG_MOVES
20859 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
20860 [(set (match_dup 2) (match_dup 1))
20861 (set (match_dup 0) (match_dup 2))]
20865 [(match_scratch:HI 2 "r")
20866 (set (match_operand:HI 0 "memory_operand" "")
20867 (match_operand:HI 1 "immediate_operand" ""))]
20868 "optimize_insn_for_speed_p ()
20869 && TARGET_SPLIT_LONG_MOVES
20870 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
20871 [(set (match_dup 2) (match_dup 1))
20872 (set (match_dup 0) (match_dup 2))]
20876 [(match_scratch:QI 2 "q")
20877 (set (match_operand:QI 0 "memory_operand" "")
20878 (match_operand:QI 1 "immediate_operand" ""))]
20879 "optimize_insn_for_speed_p ()
20880 && TARGET_SPLIT_LONG_MOVES
20881 && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
20882 [(set (match_dup 2) (match_dup 1))
20883 (set (match_dup 0) (match_dup 2))]
20886 ;; Don't compare memory with zero, load and use a test instead.
20888 [(set (match_operand 0 "flags_reg_operand" "")
20889 (match_operator 1 "compare_operator"
20890 [(match_operand:SI 2 "memory_operand" "")
20892 (match_scratch:SI 3 "r")]
20893 "optimize_insn_for_speed_p () && ix86_match_ccmode (insn, CCNOmode)"
20894 [(set (match_dup 3) (match_dup 2))
20895 (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
20898 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
20899 ;; Don't split NOTs with a displacement operand, because resulting XOR
20900 ;; will not be pairable anyway.
20902 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
20903 ;; represented using a modRM byte. The XOR replacement is long decoded,
20904 ;; so this split helps here as well.
20906 ;; Note: Can't do this as a regular split because we can't get proper
20907 ;; lifetime information then.
20910 [(set (match_operand:SI 0 "nonimmediate_operand" "")
20911 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
20912 "optimize_insn_for_speed_p ()
20913 && ((TARGET_NOT_UNPAIRABLE
20914 && (!MEM_P (operands[0])
20915 || !memory_displacement_operand (operands[0], SImode)))
20916 || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], SImode)))
20917 && peep2_regno_dead_p (0, FLAGS_REG)"
20918 [(parallel [(set (match_dup 0)
20919 (xor:SI (match_dup 1) (const_int -1)))
20920 (clobber (reg:CC FLAGS_REG))])]
20924 [(set (match_operand:HI 0 "nonimmediate_operand" "")
20925 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
20926 "optimize_insn_for_speed_p ()
20927 && ((TARGET_NOT_UNPAIRABLE
20928 && (!MEM_P (operands[0])
20929 || !memory_displacement_operand (operands[0], HImode)))
20930 || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], HImode)))
20931 && peep2_regno_dead_p (0, FLAGS_REG)"
20932 [(parallel [(set (match_dup 0)
20933 (xor:HI (match_dup 1) (const_int -1)))
20934 (clobber (reg:CC FLAGS_REG))])]
20938 [(set (match_operand:QI 0 "nonimmediate_operand" "")
20939 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
20940 "optimize_insn_for_speed_p ()
20941 && ((TARGET_NOT_UNPAIRABLE
20942 && (!MEM_P (operands[0])
20943 || !memory_displacement_operand (operands[0], QImode)))
20944 || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], QImode)))
20945 && peep2_regno_dead_p (0, FLAGS_REG)"
20946 [(parallel [(set (match_dup 0)
20947 (xor:QI (match_dup 1) (const_int -1)))
20948 (clobber (reg:CC FLAGS_REG))])]
20951 ;; Non pairable "test imm, reg" instructions can be translated to
20952 ;; "and imm, reg" if reg dies. The "and" form is also shorter (one
20953 ;; byte opcode instead of two, have a short form for byte operands),
20954 ;; so do it for other CPUs as well. Given that the value was dead,
20955 ;; this should not create any new dependencies. Pass on the sub-word
20956 ;; versions if we're concerned about partial register stalls.
20959 [(set (match_operand 0 "flags_reg_operand" "")
20960 (match_operator 1 "compare_operator"
20961 [(and:SI (match_operand:SI 2 "register_operand" "")
20962 (match_operand:SI 3 "immediate_operand" ""))
20964 "ix86_match_ccmode (insn, CCNOmode)
20965 && (true_regnum (operands[2]) != AX_REG
20966 || satisfies_constraint_K (operands[3]))
20967 && peep2_reg_dead_p (1, operands[2])"
20969 [(set (match_dup 0)
20970 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
20973 (and:SI (match_dup 2) (match_dup 3)))])]
20976 ;; We don't need to handle HImode case, because it will be promoted to SImode
20977 ;; on ! TARGET_PARTIAL_REG_STALL
20980 [(set (match_operand 0 "flags_reg_operand" "")
20981 (match_operator 1 "compare_operator"
20982 [(and:QI (match_operand:QI 2 "register_operand" "")
20983 (match_operand:QI 3 "immediate_operand" ""))
20985 "! TARGET_PARTIAL_REG_STALL
20986 && ix86_match_ccmode (insn, CCNOmode)
20987 && true_regnum (operands[2]) != AX_REG
20988 && peep2_reg_dead_p (1, operands[2])"
20990 [(set (match_dup 0)
20991 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
20994 (and:QI (match_dup 2) (match_dup 3)))])]
20998 [(set (match_operand 0 "flags_reg_operand" "")
20999 (match_operator 1 "compare_operator"
21002 (match_operand 2 "ext_register_operand" "")
21005 (match_operand 3 "const_int_operand" ""))
21007 "! TARGET_PARTIAL_REG_STALL
21008 && ix86_match_ccmode (insn, CCNOmode)
21009 && true_regnum (operands[2]) != AX_REG
21010 && peep2_reg_dead_p (1, operands[2])"
21011 [(parallel [(set (match_dup 0)
21020 (set (zero_extract:SI (match_dup 2)
21031 ;; Don't do logical operations with memory inputs.
21033 [(match_scratch:SI 2 "r")
21034 (parallel [(set (match_operand:SI 0 "register_operand" "")
21035 (match_operator:SI 3 "arith_or_logical_operator"
21037 (match_operand:SI 1 "memory_operand" "")]))
21038 (clobber (reg:CC FLAGS_REG))])]
21039 "optimize_insn_for_speed_p () && ! TARGET_READ_MODIFY"
21040 [(set (match_dup 2) (match_dup 1))
21041 (parallel [(set (match_dup 0)
21042 (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
21043 (clobber (reg:CC FLAGS_REG))])]
21047 [(match_scratch:SI 2 "r")
21048 (parallel [(set (match_operand:SI 0 "register_operand" "")
21049 (match_operator:SI 3 "arith_or_logical_operator"
21050 [(match_operand:SI 1 "memory_operand" "")
21052 (clobber (reg:CC FLAGS_REG))])]
21053 "optimize_insn_for_speed_p () && ! TARGET_READ_MODIFY"
21054 [(set (match_dup 2) (match_dup 1))
21055 (parallel [(set (match_dup 0)
21056 (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
21057 (clobber (reg:CC FLAGS_REG))])]
21060 ;; Prefer Load+RegOp to Mov+MemOp. Watch out for cases when the memory address
21061 ;; refers to the destination of the load!
21064 [(set (match_operand:SI 0 "register_operand" "")
21065 (match_operand:SI 1 "register_operand" ""))
21066 (parallel [(set (match_dup 0)
21067 (match_operator:SI 3 "commutative_operator"
21069 (match_operand:SI 2 "memory_operand" "")]))
21070 (clobber (reg:CC FLAGS_REG))])]
21071 "REGNO (operands[0]) != REGNO (operands[1])
21072 && GENERAL_REGNO_P (REGNO (operands[0]))
21073 && GENERAL_REGNO_P (REGNO (operands[1]))"
21074 [(set (match_dup 0) (match_dup 4))
21075 (parallel [(set (match_dup 0)
21076 (match_op_dup 3 [(match_dup 0) (match_dup 1)]))
21077 (clobber (reg:CC FLAGS_REG))])]
21078 "operands[4] = replace_rtx (operands[2], operands[0], operands[1]);")
21081 [(set (match_operand 0 "register_operand" "")
21082 (match_operand 1 "register_operand" ""))
21084 (match_operator 3 "commutative_operator"
21086 (match_operand 2 "memory_operand" "")]))]
21087 "REGNO (operands[0]) != REGNO (operands[1])
21088 && ((MMX_REG_P (operands[0]) && MMX_REG_P (operands[1]))
21089 || (SSE_REG_P (operands[0]) && SSE_REG_P (operands[1])))"
21090 [(set (match_dup 0) (match_dup 2))
21092 (match_op_dup 3 [(match_dup 0) (match_dup 1)]))]
21095 ; Don't do logical operations with memory outputs
21097 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
21098 ; instruction into two 1-uop insns plus a 2-uop insn. That last has
21099 ; the same decoder scheduling characteristics as the original.
21102 [(match_scratch:SI 2 "r")
21103 (parallel [(set (match_operand:SI 0 "memory_operand" "")
21104 (match_operator:SI 3 "arith_or_logical_operator"
21106 (match_operand:SI 1 "nonmemory_operand" "")]))
21107 (clobber (reg:CC FLAGS_REG))])]
21108 "optimize_insn_for_speed_p () && ! TARGET_READ_MODIFY_WRITE"
21109 [(set (match_dup 2) (match_dup 0))
21110 (parallel [(set (match_dup 2)
21111 (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
21112 (clobber (reg:CC FLAGS_REG))])
21113 (set (match_dup 0) (match_dup 2))]
21117 [(match_scratch:SI 2 "r")
21118 (parallel [(set (match_operand:SI 0 "memory_operand" "")
21119 (match_operator:SI 3 "arith_or_logical_operator"
21120 [(match_operand:SI 1 "nonmemory_operand" "")
21122 (clobber (reg:CC FLAGS_REG))])]
21123 "optimize_insn_for_speed_p () && ! TARGET_READ_MODIFY_WRITE"
21124 [(set (match_dup 2) (match_dup 0))
21125 (parallel [(set (match_dup 2)
21126 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
21127 (clobber (reg:CC FLAGS_REG))])
21128 (set (match_dup 0) (match_dup 2))]
21131 ;; Attempt to always use XOR for zeroing registers.
21133 [(set (match_operand 0 "register_operand" "")
21134 (match_operand 1 "const0_operand" ""))]
21135 "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
21136 && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
21137 && GENERAL_REG_P (operands[0])
21138 && peep2_regno_dead_p (0, FLAGS_REG)"
21139 [(parallel [(set (match_dup 0) (const_int 0))
21140 (clobber (reg:CC FLAGS_REG))])]
21142 operands[0] = gen_lowpart (word_mode, operands[0]);
21146 [(set (strict_low_part (match_operand 0 "register_operand" ""))
21148 "(GET_MODE (operands[0]) == QImode
21149 || GET_MODE (operands[0]) == HImode)
21150 && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
21151 && peep2_regno_dead_p (0, FLAGS_REG)"
21152 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
21153 (clobber (reg:CC FLAGS_REG))])])
21155 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
21157 [(set (match_operand 0 "register_operand" "")
21159 "(GET_MODE (operands[0]) == HImode
21160 || GET_MODE (operands[0]) == SImode
21161 || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
21162 && (optimize_insn_for_size_p () || TARGET_MOVE_M1_VIA_OR)
21163 && peep2_regno_dead_p (0, FLAGS_REG)"
21164 [(parallel [(set (match_dup 0) (const_int -1))
21165 (clobber (reg:CC FLAGS_REG))])]
21166 "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
21169 ;; Attempt to convert simple leas to adds. These can be created by
21172 [(set (match_operand:SI 0 "register_operand" "")
21173 (plus:SI (match_dup 0)
21174 (match_operand:SI 1 "nonmemory_operand" "")))]
21175 "peep2_regno_dead_p (0, FLAGS_REG)"
21176 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
21177 (clobber (reg:CC FLAGS_REG))])]
21181 [(set (match_operand:SI 0 "register_operand" "")
21182 (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
21183 (match_operand:DI 2 "nonmemory_operand" "")) 0))]
21184 "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
21185 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
21186 (clobber (reg:CC FLAGS_REG))])]
21187 "operands[2] = gen_lowpart (SImode, operands[2]);")
21190 [(set (match_operand:DI 0 "register_operand" "")
21191 (plus:DI (match_dup 0)
21192 (match_operand:DI 1 "x86_64_general_operand" "")))]
21193 "peep2_regno_dead_p (0, FLAGS_REG)"
21194 [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
21195 (clobber (reg:CC FLAGS_REG))])]
21199 [(set (match_operand:SI 0 "register_operand" "")
21200 (mult:SI (match_dup 0)
21201 (match_operand:SI 1 "const_int_operand" "")))]
21202 "exact_log2 (INTVAL (operands[1])) >= 0
21203 && peep2_regno_dead_p (0, FLAGS_REG)"
21204 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
21205 (clobber (reg:CC FLAGS_REG))])]
21206 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
21209 [(set (match_operand:DI 0 "register_operand" "")
21210 (mult:DI (match_dup 0)
21211 (match_operand:DI 1 "const_int_operand" "")))]
21212 "exact_log2 (INTVAL (operands[1])) >= 0
21213 && peep2_regno_dead_p (0, FLAGS_REG)"
21214 [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
21215 (clobber (reg:CC FLAGS_REG))])]
21216 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
21219 [(set (match_operand:SI 0 "register_operand" "")
21220 (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
21221 (match_operand:DI 2 "const_int_operand" "")) 0))]
21222 "exact_log2 (INTVAL (operands[2])) >= 0
21223 && REGNO (operands[0]) == REGNO (operands[1])
21224 && peep2_regno_dead_p (0, FLAGS_REG)"
21225 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
21226 (clobber (reg:CC FLAGS_REG))])]
21227 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
21229 ;; The ESP adjustments can be done by the push and pop instructions. Resulting
21230 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On
21231 ;; many CPUs it is also faster, since special hardware to avoid esp
21232 ;; dependencies is present.
21234 ;; While some of these conversions may be done using splitters, we use peepholes
21235 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
21237 ;; Convert prologue esp subtractions to push.
21238 ;; We need register to push. In order to keep verify_flow_info happy we have
21240 ;; - use scratch and clobber it in order to avoid dependencies
21241 ;; - use already live register
21242 ;; We can't use the second way right now, since there is no reliable way how to
21243 ;; verify that given register is live. First choice will also most likely in
21244 ;; fewer dependencies. On the place of esp adjustments it is very likely that
21245 ;; call clobbered registers are dead. We may want to use base pointer as an
21246 ;; alternative when no register is available later.
21249 [(match_scratch:SI 0 "r")
21250 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
21251 (clobber (reg:CC FLAGS_REG))
21252 (clobber (mem:BLK (scratch)))])]
21253 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_4"
21254 [(clobber (match_dup 0))
21255 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
21256 (clobber (mem:BLK (scratch)))])])
21259 [(match_scratch:SI 0 "r")
21260 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
21261 (clobber (reg:CC FLAGS_REG))
21262 (clobber (mem:BLK (scratch)))])]
21263 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_8"
21264 [(clobber (match_dup 0))
21265 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
21266 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
21267 (clobber (mem:BLK (scratch)))])])
21269 ;; Convert esp subtractions to push.
21271 [(match_scratch:SI 0 "r")
21272 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
21273 (clobber (reg:CC FLAGS_REG))])]
21274 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_4"
21275 [(clobber (match_dup 0))
21276 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
21279 [(match_scratch:SI 0 "r")
21280 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
21281 (clobber (reg:CC FLAGS_REG))])]
21282 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_8"
21283 [(clobber (match_dup 0))
21284 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
21285 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
21287 ;; Convert epilogue deallocator to pop.
21289 [(match_scratch:SI 0 "r")
21290 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
21291 (clobber (reg:CC FLAGS_REG))
21292 (clobber (mem:BLK (scratch)))])]
21293 "optimize_insn_for_size_p () || !TARGET_ADD_ESP_4"
21294 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21295 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
21296 (clobber (mem:BLK (scratch)))])]
21299 ;; Two pops case is tricky, since pop causes dependency on destination register.
21300 ;; We use two registers if available.
21302 [(match_scratch:SI 0 "r")
21303 (match_scratch:SI 1 "r")
21304 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
21305 (clobber (reg:CC FLAGS_REG))
21306 (clobber (mem:BLK (scratch)))])]
21307 "optimize_insn_for_size_p () || !TARGET_ADD_ESP_8"
21308 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21309 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
21310 (clobber (mem:BLK (scratch)))])
21311 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
21312 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
21316 [(match_scratch:SI 0 "r")
21317 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
21318 (clobber (reg:CC FLAGS_REG))
21319 (clobber (mem:BLK (scratch)))])]
21320 "optimize_insn_for_size_p ()"
21321 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21322 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
21323 (clobber (mem:BLK (scratch)))])
21324 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21325 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
21328 ;; Convert esp additions to pop.
21330 [(match_scratch:SI 0 "r")
21331 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
21332 (clobber (reg:CC FLAGS_REG))])]
21334 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21335 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
21338 ;; Two pops case is tricky, since pop causes dependency on destination register.
21339 ;; We use two registers if available.
21341 [(match_scratch:SI 0 "r")
21342 (match_scratch:SI 1 "r")
21343 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
21344 (clobber (reg:CC FLAGS_REG))])]
21346 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21347 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
21348 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
21349 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
21353 [(match_scratch:SI 0 "r")
21354 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
21355 (clobber (reg:CC FLAGS_REG))])]
21356 "optimize_insn_for_size_p ()"
21357 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21358 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
21359 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
21360 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
21363 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
21364 ;; required and register dies. Similarly for 128 to -128.
21366 [(set (match_operand 0 "flags_reg_operand" "")
21367 (match_operator 1 "compare_operator"
21368 [(match_operand 2 "register_operand" "")
21369 (match_operand 3 "const_int_operand" "")]))]
21370 "(((!TARGET_FUSE_CMP_AND_BRANCH || optimize_insn_for_size_p ())
21371 && incdec_operand (operands[3], GET_MODE (operands[3])))
21372 || (!TARGET_FUSE_CMP_AND_BRANCH
21373 && INTVAL (operands[3]) == 128))
21374 && ix86_match_ccmode (insn, CCGCmode)
21375 && peep2_reg_dead_p (1, operands[2])"
21376 [(parallel [(set (match_dup 0)
21377 (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
21378 (clobber (match_dup 2))])]
21382 [(match_scratch:DI 0 "r")
21383 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
21384 (clobber (reg:CC FLAGS_REG))
21385 (clobber (mem:BLK (scratch)))])]
21386 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_4"
21387 [(clobber (match_dup 0))
21388 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
21389 (clobber (mem:BLK (scratch)))])])
21392 [(match_scratch:DI 0 "r")
21393 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
21394 (clobber (reg:CC FLAGS_REG))
21395 (clobber (mem:BLK (scratch)))])]
21396 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_8"
21397 [(clobber (match_dup 0))
21398 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
21399 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
21400 (clobber (mem:BLK (scratch)))])])
21402 ;; Convert esp subtractions to push.
21404 [(match_scratch:DI 0 "r")
21405 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
21406 (clobber (reg:CC FLAGS_REG))])]
21407 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_4"
21408 [(clobber (match_dup 0))
21409 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
21412 [(match_scratch:DI 0 "r")
21413 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
21414 (clobber (reg:CC FLAGS_REG))])]
21415 "optimize_insn_for_size_p () || !TARGET_SUB_ESP_8"
21416 [(clobber (match_dup 0))
21417 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
21418 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
21420 ;; Convert epilogue deallocator to pop.
21422 [(match_scratch:DI 0 "r")
21423 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
21424 (clobber (reg:CC FLAGS_REG))
21425 (clobber (mem:BLK (scratch)))])]
21426 "optimize_insn_for_size_p () || !TARGET_ADD_ESP_4"
21427 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21428 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
21429 (clobber (mem:BLK (scratch)))])]
21432 ;; Two pops case is tricky, since pop causes dependency on destination register.
21433 ;; We use two registers if available.
21435 [(match_scratch:DI 0 "r")
21436 (match_scratch:DI 1 "r")
21437 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
21438 (clobber (reg:CC FLAGS_REG))
21439 (clobber (mem:BLK (scratch)))])]
21440 "optimize_insn_for_size_p () || !TARGET_ADD_ESP_8"
21441 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21442 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
21443 (clobber (mem:BLK (scratch)))])
21444 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
21445 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
21449 [(match_scratch:DI 0 "r")
21450 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
21451 (clobber (reg:CC FLAGS_REG))
21452 (clobber (mem:BLK (scratch)))])]
21453 "optimize_insn_for_size_p ()"
21454 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21455 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
21456 (clobber (mem:BLK (scratch)))])
21457 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21458 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
21461 ;; Convert esp additions to pop.
21463 [(match_scratch:DI 0 "r")
21464 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
21465 (clobber (reg:CC FLAGS_REG))])]
21467 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21468 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
21471 ;; Two pops case is tricky, since pop causes dependency on destination register.
21472 ;; We use two registers if available.
21474 [(match_scratch:DI 0 "r")
21475 (match_scratch:DI 1 "r")
21476 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
21477 (clobber (reg:CC FLAGS_REG))])]
21479 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21480 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
21481 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
21482 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
21486 [(match_scratch:DI 0 "r")
21487 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
21488 (clobber (reg:CC FLAGS_REG))])]
21489 "optimize_insn_for_size_p ()"
21490 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21491 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
21492 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
21493 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
21496 ;; Convert imul by three, five and nine into lea
21499 [(set (match_operand:SI 0 "register_operand" "")
21500 (mult:SI (match_operand:SI 1 "register_operand" "")
21501 (match_operand:SI 2 "const_int_operand" "")))
21502 (clobber (reg:CC FLAGS_REG))])]
21503 "INTVAL (operands[2]) == 3
21504 || INTVAL (operands[2]) == 5
21505 || INTVAL (operands[2]) == 9"
21506 [(set (match_dup 0)
21507 (plus:SI (mult:SI (match_dup 1) (match_dup 2))
21509 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
21513 [(set (match_operand:SI 0 "register_operand" "")
21514 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
21515 (match_operand:SI 2 "const_int_operand" "")))
21516 (clobber (reg:CC FLAGS_REG))])]
21517 "optimize_insn_for_speed_p ()
21518 && (INTVAL (operands[2]) == 3
21519 || INTVAL (operands[2]) == 5
21520 || INTVAL (operands[2]) == 9)"
21521 [(set (match_dup 0) (match_dup 1))
21523 (plus:SI (mult:SI (match_dup 0) (match_dup 2))
21525 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
21529 [(set (match_operand:DI 0 "register_operand" "")
21530 (mult:DI (match_operand:DI 1 "register_operand" "")
21531 (match_operand:DI 2 "const_int_operand" "")))
21532 (clobber (reg:CC FLAGS_REG))])]
21534 && (INTVAL (operands[2]) == 3
21535 || INTVAL (operands[2]) == 5
21536 || INTVAL (operands[2]) == 9)"
21537 [(set (match_dup 0)
21538 (plus:DI (mult:DI (match_dup 1) (match_dup 2))
21540 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
21544 [(set (match_operand:DI 0 "register_operand" "")
21545 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
21546 (match_operand:DI 2 "const_int_operand" "")))
21547 (clobber (reg:CC FLAGS_REG))])]
21549 && optimize_insn_for_speed_p ()
21550 && (INTVAL (operands[2]) == 3
21551 || INTVAL (operands[2]) == 5
21552 || INTVAL (operands[2]) == 9)"
21553 [(set (match_dup 0) (match_dup 1))
21555 (plus:DI (mult:DI (match_dup 0) (match_dup 2))
21557 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
21559 ;; Imul $32bit_imm, mem, reg is vector decoded, while
21560 ;; imul $32bit_imm, reg, reg is direct decoded.
21562 [(match_scratch:DI 3 "r")
21563 (parallel [(set (match_operand:DI 0 "register_operand" "")
21564 (mult:DI (match_operand:DI 1 "memory_operand" "")
21565 (match_operand:DI 2 "immediate_operand" "")))
21566 (clobber (reg:CC FLAGS_REG))])]
21567 "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
21568 && !satisfies_constraint_K (operands[2])"
21569 [(set (match_dup 3) (match_dup 1))
21570 (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
21571 (clobber (reg:CC FLAGS_REG))])]
21575 [(match_scratch:SI 3 "r")
21576 (parallel [(set (match_operand:SI 0 "register_operand" "")
21577 (mult:SI (match_operand:SI 1 "memory_operand" "")
21578 (match_operand:SI 2 "immediate_operand" "")))
21579 (clobber (reg:CC FLAGS_REG))])]
21580 "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
21581 && !satisfies_constraint_K (operands[2])"
21582 [(set (match_dup 3) (match_dup 1))
21583 (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
21584 (clobber (reg:CC FLAGS_REG))])]
21588 [(match_scratch:SI 3 "r")
21589 (parallel [(set (match_operand:DI 0 "register_operand" "")
21591 (mult:SI (match_operand:SI 1 "memory_operand" "")
21592 (match_operand:SI 2 "immediate_operand" ""))))
21593 (clobber (reg:CC FLAGS_REG))])]
21594 "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
21595 && !satisfies_constraint_K (operands[2])"
21596 [(set (match_dup 3) (match_dup 1))
21597 (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
21598 (clobber (reg:CC FLAGS_REG))])]
21601 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
21602 ;; Convert it into imul reg, reg
21603 ;; It would be better to force assembler to encode instruction using long
21604 ;; immediate, but there is apparently no way to do so.
21606 [(parallel [(set (match_operand:DI 0 "register_operand" "")
21607 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
21608 (match_operand:DI 2 "const_int_operand" "")))
21609 (clobber (reg:CC FLAGS_REG))])
21610 (match_scratch:DI 3 "r")]
21611 "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()
21612 && satisfies_constraint_K (operands[2])"
21613 [(set (match_dup 3) (match_dup 2))
21614 (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
21615 (clobber (reg:CC FLAGS_REG))])]
21617 if (!rtx_equal_p (operands[0], operands[1]))
21618 emit_move_insn (operands[0], operands[1]);
21622 [(parallel [(set (match_operand:SI 0 "register_operand" "")
21623 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
21624 (match_operand:SI 2 "const_int_operand" "")))
21625 (clobber (reg:CC FLAGS_REG))])
21626 (match_scratch:SI 3 "r")]
21627 "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()
21628 && satisfies_constraint_K (operands[2])"
21629 [(set (match_dup 3) (match_dup 2))
21630 (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
21631 (clobber (reg:CC FLAGS_REG))])]
21633 if (!rtx_equal_p (operands[0], operands[1]))
21634 emit_move_insn (operands[0], operands[1]);
21638 [(parallel [(set (match_operand:HI 0 "register_operand" "")
21639 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
21640 (match_operand:HI 2 "immediate_operand" "")))
21641 (clobber (reg:CC FLAGS_REG))])
21642 (match_scratch:HI 3 "r")]
21643 "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()"
21644 [(set (match_dup 3) (match_dup 2))
21645 (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
21646 (clobber (reg:CC FLAGS_REG))])]
21648 if (!rtx_equal_p (operands[0], operands[1]))
21649 emit_move_insn (operands[0], operands[1]);
21652 ;; After splitting up read-modify operations, array accesses with memory
21653 ;; operands might end up in form:
21655 ;; movl 4(%esp), %edx
21657 ;; instead of pre-splitting:
21659 ;; addl 4(%esp), %eax
21661 ;; movl 4(%esp), %edx
21662 ;; leal (%edx,%eax,4), %eax
21665 [(parallel [(set (match_operand 0 "register_operand" "")
21666 (ashift (match_operand 1 "register_operand" "")
21667 (match_operand 2 "const_int_operand" "")))
21668 (clobber (reg:CC FLAGS_REG))])
21669 (set (match_operand 3 "register_operand")
21670 (match_operand 4 "x86_64_general_operand" ""))
21671 (parallel [(set (match_operand 5 "register_operand" "")
21672 (plus (match_operand 6 "register_operand" "")
21673 (match_operand 7 "register_operand" "")))
21674 (clobber (reg:CC FLAGS_REG))])]
21675 "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3
21676 /* Validate MODE for lea. */
21677 && ((!TARGET_PARTIAL_REG_STALL
21678 && (GET_MODE (operands[0]) == QImode
21679 || GET_MODE (operands[0]) == HImode))
21680 || GET_MODE (operands[0]) == SImode
21681 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
21682 /* We reorder load and the shift. */
21683 && !rtx_equal_p (operands[1], operands[3])
21684 && !reg_overlap_mentioned_p (operands[0], operands[4])
21685 /* Last PLUS must consist of operand 0 and 3. */
21686 && !rtx_equal_p (operands[0], operands[3])
21687 && (rtx_equal_p (operands[3], operands[6])
21688 || rtx_equal_p (operands[3], operands[7]))
21689 && (rtx_equal_p (operands[0], operands[6])
21690 || rtx_equal_p (operands[0], operands[7]))
21691 /* The intermediate operand 0 must die or be same as output. */
21692 && (rtx_equal_p (operands[0], operands[5])
21693 || peep2_reg_dead_p (3, operands[0]))"
21694 [(set (match_dup 3) (match_dup 4))
21695 (set (match_dup 0) (match_dup 1))]
21697 enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode;
21698 int scale = 1 << INTVAL (operands[2]);
21699 rtx index = gen_lowpart (Pmode, operands[1]);
21700 rtx base = gen_lowpart (Pmode, operands[3]);
21701 rtx dest = gen_lowpart (mode, operands[5]);
21703 operands[1] = gen_rtx_PLUS (Pmode, base,
21704 gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
21706 operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
21707 operands[0] = dest;
21710 ;; Call-value patterns last so that the wildcard operand does not
21711 ;; disrupt insn-recog's switch tables.
21713 (define_insn "*call_value_pop_0"
21714 [(set (match_operand 0 "" "")
21715 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
21716 (match_operand:SI 2 "" "")))
21717 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
21718 (match_operand:SI 3 "immediate_operand" "")))]
21721 if (SIBLING_CALL_P (insn))
21724 return "call\t%P1";
21726 [(set_attr "type" "callv")])
21728 (define_insn "*call_value_pop_1"
21729 [(set (match_operand 0 "" "")
21730 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
21731 (match_operand:SI 2 "" "")))
21732 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
21733 (match_operand:SI 3 "immediate_operand" "i")))]
21736 if (constant_call_address_operand (operands[1], Pmode))
21738 if (SIBLING_CALL_P (insn))
21741 return "call\t%P1";
21743 if (SIBLING_CALL_P (insn))
21746 return "call\t%A1";
21748 [(set_attr "type" "callv")])
21750 (define_insn "*call_value_0"
21751 [(set (match_operand 0 "" "")
21752 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
21753 (match_operand:SI 2 "" "")))]
21756 if (SIBLING_CALL_P (insn))
21759 return "call\t%P1";
21761 [(set_attr "type" "callv")])
21763 (define_insn "*call_value_0_rex64"
21764 [(set (match_operand 0 "" "")
21765 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
21766 (match_operand:DI 2 "const_int_operand" "")))]
21769 if (SIBLING_CALL_P (insn))
21772 return "call\t%P1";
21774 [(set_attr "type" "callv")])
21776 (define_insn "*call_value_0_rex64_ms_sysv"
21777 [(set (match_operand 0 "" "")
21778 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
21779 (match_operand:DI 2 "const_int_operand" "")))
21780 (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
21781 (clobber (reg:TI XMM6_REG))
21782 (clobber (reg:TI XMM7_REG))
21783 (clobber (reg:TI XMM8_REG))
21784 (clobber (reg:TI XMM9_REG))
21785 (clobber (reg:TI XMM10_REG))
21786 (clobber (reg:TI XMM11_REG))
21787 (clobber (reg:TI XMM12_REG))
21788 (clobber (reg:TI XMM13_REG))
21789 (clobber (reg:TI XMM14_REG))
21790 (clobber (reg:TI XMM15_REG))
21791 (clobber (reg:DI SI_REG))
21792 (clobber (reg:DI DI_REG))]
21793 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
21795 if (SIBLING_CALL_P (insn))
21798 return "call\t%P1";
21800 [(set_attr "type" "callv")])
21802 (define_insn "*call_value_1"
21803 [(set (match_operand 0 "" "")
21804 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
21805 (match_operand:SI 2 "" "")))]
21806 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
21808 if (constant_call_address_operand (operands[1], Pmode))
21809 return "call\t%P1";
21810 return "call\t%A1";
21812 [(set_attr "type" "callv")])
21814 (define_insn "*sibcall_value_1"
21815 [(set (match_operand 0 "" "")
21816 (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
21817 (match_operand:SI 2 "" "")))]
21818 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
21820 if (constant_call_address_operand (operands[1], Pmode))
21824 [(set_attr "type" "callv")])
21826 (define_insn "*call_value_1_rex64"
21827 [(set (match_operand 0 "" "")
21828 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
21829 (match_operand:DI 2 "" "")))]
21830 "!SIBLING_CALL_P (insn) && TARGET_64BIT
21831 && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
21833 if (constant_call_address_operand (operands[1], Pmode))
21834 return "call\t%P1";
21835 return "call\t%A1";
21837 [(set_attr "type" "callv")])
21839 (define_insn "*call_value_1_rex64_ms_sysv"
21840 [(set (match_operand 0 "" "")
21841 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
21842 (match_operand:DI 2 "" "")))
21843 (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
21844 (clobber (reg:TI 27))
21845 (clobber (reg:TI 28))
21846 (clobber (reg:TI 45))
21847 (clobber (reg:TI 46))
21848 (clobber (reg:TI 47))
21849 (clobber (reg:TI 48))
21850 (clobber (reg:TI 49))
21851 (clobber (reg:TI 50))
21852 (clobber (reg:TI 51))
21853 (clobber (reg:TI 52))
21854 (clobber (reg:DI SI_REG))
21855 (clobber (reg:DI DI_REG))]
21856 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
21858 if (constant_call_address_operand (operands[1], Pmode))
21859 return "call\t%P1";
21860 return "call\t%A1";
21862 [(set_attr "type" "callv")])
21864 (define_insn "*call_value_1_rex64_large"
21865 [(set (match_operand 0 "" "")
21866 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rm"))
21867 (match_operand:DI 2 "" "")))]
21868 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
21870 [(set_attr "type" "callv")])
21872 (define_insn "*sibcall_value_1_rex64"
21873 [(set (match_operand 0 "" "")
21874 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
21875 (match_operand:DI 2 "" "")))]
21876 "SIBLING_CALL_P (insn) && TARGET_64BIT"
21878 [(set_attr "type" "callv")])
21880 (define_insn "*sibcall_value_1_rex64_v"
21881 [(set (match_operand 0 "" "")
21882 (call (mem:QI (reg:DI R11_REG))
21883 (match_operand:DI 1 "" "")))]
21884 "SIBLING_CALL_P (insn) && TARGET_64BIT"
21886 [(set_attr "type" "callv")])
21888 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
21889 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
21890 ;; caught for use by garbage collectors and the like. Using an insn that
21891 ;; maps to SIGILL makes it more likely the program will rightfully die.
21892 ;; Keeping with tradition, "6" is in honor of #UD.
21893 (define_insn "trap"
21894 [(trap_if (const_int 1) (const_int 6))]
21896 { return ASM_SHORT "0x0b0f"; }
21897 [(set_attr "length" "2")])
21899 (define_expand "sse_prologue_save"
21900 [(parallel [(set (match_operand:BLK 0 "" "")
21901 (unspec:BLK [(reg:DI 21)
21908 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
21909 (use (match_operand:DI 1 "register_operand" ""))
21910 (use (match_operand:DI 2 "immediate_operand" ""))
21911 (use (label_ref:DI (match_operand 3 "" "")))])]
21915 (define_insn "*sse_prologue_save_insn"
21916 [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
21917 (match_operand:DI 4 "const_int_operand" "n")))
21918 (unspec:BLK [(reg:DI 21)
21925 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
21926 (use (match_operand:DI 1 "register_operand" "r"))
21927 (use (match_operand:DI 2 "const_int_operand" "i"))
21928 (use (label_ref:DI (match_operand 3 "" "X")))]
21930 && INTVAL (operands[4]) + X86_64_SSE_REGPARM_MAX * 16 - 16 < 128
21931 && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
21934 operands[0] = gen_rtx_MEM (Pmode,
21935 gen_rtx_PLUS (Pmode, operands[0], operands[4]));
21936 /* VEX instruction with a REX prefix will #UD. */
21937 if (TARGET_AVX && GET_CODE (XEXP (operands[0], 0)) != PLUS)
21938 gcc_unreachable ();
21940 output_asm_insn ("jmp\t%A1", operands);
21941 for (i = X86_64_SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
21943 operands[4] = adjust_address (operands[0], DImode, i*16);
21944 operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
21945 PUT_MODE (operands[4], TImode);
21946 if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
21947 output_asm_insn ("rex", operands);
21948 output_asm_insn ("%vmovaps\t{%5, %4|%4, %5}", operands);
21950 (*targetm.asm_out.internal_label) (asm_out_file, "L",
21951 CODE_LABEL_NUMBER (operands[3]));
21954 [(set_attr "type" "other")
21955 (set_attr "length_immediate" "0")
21956 (set_attr "length_address" "0")
21957 (set (attr "length")
21959 (eq (symbol_ref "TARGET_AVX") (const_int 0))
21960 (const_string "34")
21961 (const_string "42")))
21962 (set_attr "memory" "store")
21963 (set_attr "modrm" "0")
21964 (set_attr "prefix" "maybe_vex")
21965 (set_attr "mode" "DI")])
21967 (define_expand "prefetch"
21968 [(prefetch (match_operand 0 "address_operand" "")
21969 (match_operand:SI 1 "const_int_operand" "")
21970 (match_operand:SI 2 "const_int_operand" ""))]
21971 "TARGET_PREFETCH_SSE || TARGET_3DNOW"
21973 int rw = INTVAL (operands[1]);
21974 int locality = INTVAL (operands[2]);
21976 gcc_assert (rw == 0 || rw == 1);
21977 gcc_assert (locality >= 0 && locality <= 3);
21978 gcc_assert (GET_MODE (operands[0]) == Pmode
21979 || GET_MODE (operands[0]) == VOIDmode);
21981 /* Use 3dNOW prefetch in case we are asking for write prefetch not
21982 supported by SSE counterpart or the SSE prefetch is not available
21983 (K6 machines). Otherwise use SSE prefetch as it allows specifying
21985 if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
21986 operands[2] = GEN_INT (3);
21988 operands[1] = const0_rtx;
21991 (define_insn "*prefetch_sse"
21992 [(prefetch (match_operand:SI 0 "address_operand" "p")
21994 (match_operand:SI 1 "const_int_operand" ""))]
21995 "TARGET_PREFETCH_SSE && !TARGET_64BIT"
21997 static const char * const patterns[4] = {
21998 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
22001 int locality = INTVAL (operands[1]);
22002 gcc_assert (locality >= 0 && locality <= 3);
22004 return patterns[locality];
22006 [(set_attr "type" "sse")
22007 (set_attr "atom_sse_attr" "prefetch")
22008 (set_attr "memory" "none")])
22010 (define_insn "*prefetch_sse_rex"
22011 [(prefetch (match_operand:DI 0 "address_operand" "p")
22013 (match_operand:SI 1 "const_int_operand" ""))]
22014 "TARGET_PREFETCH_SSE && TARGET_64BIT"
22016 static const char * const patterns[4] = {
22017 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
22020 int locality = INTVAL (operands[1]);
22021 gcc_assert (locality >= 0 && locality <= 3);
22023 return patterns[locality];
22025 [(set_attr "type" "sse")
22026 (set_attr "atom_sse_attr" "prefetch")
22027 (set_attr "memory" "none")])
22029 (define_insn "*prefetch_3dnow"
22030 [(prefetch (match_operand:SI 0 "address_operand" "p")
22031 (match_operand:SI 1 "const_int_operand" "n")
22033 "TARGET_3DNOW && !TARGET_64BIT"
22035 if (INTVAL (operands[1]) == 0)
22036 return "prefetch\t%a0";
22038 return "prefetchw\t%a0";
22040 [(set_attr "type" "mmx")
22041 (set_attr "memory" "none")])
22043 (define_insn "*prefetch_3dnow_rex"
22044 [(prefetch (match_operand:DI 0 "address_operand" "p")
22045 (match_operand:SI 1 "const_int_operand" "n")
22047 "TARGET_3DNOW && TARGET_64BIT"
22049 if (INTVAL (operands[1]) == 0)
22050 return "prefetch\t%a0";
22052 return "prefetchw\t%a0";
22054 [(set_attr "type" "mmx")
22055 (set_attr "memory" "none")])
22057 (define_expand "stack_protect_set"
22058 [(match_operand 0 "memory_operand" "")
22059 (match_operand 1 "memory_operand" "")]
22062 #ifdef TARGET_THREAD_SSP_OFFSET
22064 emit_insn (gen_stack_tls_protect_set_di (operands[0],
22065 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
22067 emit_insn (gen_stack_tls_protect_set_si (operands[0],
22068 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
22071 emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
22073 emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
22078 (define_insn "stack_protect_set_si"
22079 [(set (match_operand:SI 0 "memory_operand" "=m")
22080 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
22081 (set (match_scratch:SI 2 "=&r") (const_int 0))
22082 (clobber (reg:CC FLAGS_REG))]
22084 "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
22085 [(set_attr "type" "multi")])
22087 (define_insn "stack_protect_set_di"
22088 [(set (match_operand:DI 0 "memory_operand" "=m")
22089 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
22090 (set (match_scratch:DI 2 "=&r") (const_int 0))
22091 (clobber (reg:CC FLAGS_REG))]
22093 "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
22094 [(set_attr "type" "multi")])
22096 (define_insn "stack_tls_protect_set_si"
22097 [(set (match_operand:SI 0 "memory_operand" "=m")
22098 (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
22099 (set (match_scratch:SI 2 "=&r") (const_int 0))
22100 (clobber (reg:CC FLAGS_REG))]
22102 "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
22103 [(set_attr "type" "multi")])
22105 (define_insn "stack_tls_protect_set_di"
22106 [(set (match_operand:DI 0 "memory_operand" "=m")
22107 (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
22108 (set (match_scratch:DI 2 "=&r") (const_int 0))
22109 (clobber (reg:CC FLAGS_REG))]
22112 /* The kernel uses a different segment register for performance reasons; a
22113 system call would not have to trash the userspace segment register,
22114 which would be expensive */
22115 if (ix86_cmodel != CM_KERNEL)
22116 return "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
22118 return "mov{q}\t{%%gs:%P1, %2|%2, QWORD PTR gs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
22120 [(set_attr "type" "multi")])
22122 (define_expand "stack_protect_test"
22123 [(match_operand 0 "memory_operand" "")
22124 (match_operand 1 "memory_operand" "")
22125 (match_operand 2 "" "")]
22128 rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
22130 #ifdef TARGET_THREAD_SSP_OFFSET
22132 emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
22133 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
22135 emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
22136 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
22139 emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
22141 emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
22144 emit_jump_insn (gen_cbranchcc4 (gen_rtx_EQ (VOIDmode, flags, const0_rtx),
22145 flags, const0_rtx, operands[2]));
22149 (define_insn "stack_protect_test_si"
22150 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
22151 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
22152 (match_operand:SI 2 "memory_operand" "m")]
22154 (clobber (match_scratch:SI 3 "=&r"))]
22156 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
22157 [(set_attr "type" "multi")])
22159 (define_insn "stack_protect_test_di"
22160 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
22161 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
22162 (match_operand:DI 2 "memory_operand" "m")]
22164 (clobber (match_scratch:DI 3 "=&r"))]
22166 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
22167 [(set_attr "type" "multi")])
22169 (define_insn "stack_tls_protect_test_si"
22170 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
22171 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
22172 (match_operand:SI 2 "const_int_operand" "i")]
22173 UNSPEC_SP_TLS_TEST))
22174 (clobber (match_scratch:SI 3 "=r"))]
22176 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR gs:%P2}"
22177 [(set_attr "type" "multi")])
22179 (define_insn "stack_tls_protect_test_di"
22180 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
22181 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
22182 (match_operand:DI 2 "const_int_operand" "i")]
22183 UNSPEC_SP_TLS_TEST))
22184 (clobber (match_scratch:DI 3 "=r"))]
22187 /* The kernel uses a different segment register for performance reasons; a
22188 system call would not have to trash the userspace segment register,
22189 which would be expensive */
22190 if (ix86_cmodel != CM_KERNEL)
22191 return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR fs:%P2}";
22193 return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%gs:%P2, %3|%3, QWORD PTR gs:%P2}";
22195 [(set_attr "type" "multi")])
22197 (define_mode_iterator CRC32MODE [QI HI SI])
22198 (define_mode_attr crc32modesuffix [(QI "b") (HI "w") (SI "l")])
22199 (define_mode_attr crc32modeconstraint [(QI "qm") (HI "rm") (SI "rm")])
22201 (define_insn "sse4_2_crc32<mode>"
22202 [(set (match_operand:SI 0 "register_operand" "=r")
22204 [(match_operand:SI 1 "register_operand" "0")
22205 (match_operand:CRC32MODE 2 "nonimmediate_operand" "<crc32modeconstraint>")]
22208 "crc32<crc32modesuffix>\t{%2, %0|%0, %2}"
22209 [(set_attr "type" "sselog1")
22210 (set_attr "prefix_rep" "1")
22211 (set_attr "prefix_extra" "1")
22212 (set_attr "mode" "SI")])
22214 (define_insn "sse4_2_crc32di"
22215 [(set (match_operand:DI 0 "register_operand" "=r")
22217 [(match_operand:DI 1 "register_operand" "0")
22218 (match_operand:DI 2 "nonimmediate_operand" "rm")]
22220 "TARGET_SSE4_2 && TARGET_64BIT"
22221 "crc32q\t{%2, %0|%0, %2}"
22222 [(set_attr "type" "sselog1")
22223 (set_attr "prefix_rep" "1")
22224 (set_attr "prefix_extra" "1")
22225 (set_attr "mode" "DI")])
22229 (include "sync.md")