OSDN Git Service

Revert delta 190174
[pf3gnuchains/gcc-fork.git] / gcc / config / i386 / i386.md
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, 2010, 2011, 2012
4 ;; Free Software Foundation, Inc.
5 ;; Mostly by William Schelter.
6 ;; x86_64 support added by Jan Hubicka
7 ;;
8 ;; This file is part of GCC.
9 ;;
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)
13 ;; any later version.
14 ;;
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.
19 ;;
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/>.  */
23 ;;
24 ;; The original PO technology requires these to be ordered by speed,
25 ;; so that assigner will pick the fastest.
26 ;;
27 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
28 ;;
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 ;; F,f -- likewise, but for floating-point.
34 ;; O -- if HAVE_AS_IX86_CMOV_SUN_SYNTAX, expand to "w.", "l." or "q.",
35 ;;      otherwise nothing
36 ;; R -- print the prefix for register names.
37 ;; z -- print the opcode suffix for the size of the current operand.
38 ;; Z -- likewise, with special suffixes for x87 instructions.
39 ;; * -- print a star (in certain assembler syntax)
40 ;; A -- print an absolute memory reference.
41 ;; E -- print address with DImode register names if TARGET_64BIT.
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
44 ;;      delimiter.
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 ;; p -- print raw symbol name.
58 ;; X -- don't print any sort of PIC '@' suffix for a symbol.
59 ;; & -- print some in-use local-dynamic symbol name.
60 ;; H -- print a memory address offset by 8; used for sse high-parts
61 ;; Y -- print condition for XOP pcom* instruction.
62 ;; + -- print a branch hint as 'cs' or 'ds' prefix
63 ;; ; -- print a semicolon (after prefixes due to bug in older gas).
64 ;; @ -- print a segment register of thread base pointer load
65
66 (define_c_enum "unspec" [
67   ;; Relocation specifiers
68   UNSPEC_GOT
69   UNSPEC_GOTOFF
70   UNSPEC_GOTPCREL
71   UNSPEC_GOTTPOFF
72   UNSPEC_TPOFF
73   UNSPEC_NTPOFF
74   UNSPEC_DTPOFF
75   UNSPEC_GOTNTPOFF
76   UNSPEC_INDNTPOFF
77   UNSPEC_PLTOFF
78   UNSPEC_MACHOPIC_OFFSET
79   UNSPEC_PCREL
80
81   ;; Prologue support
82   UNSPEC_STACK_ALLOC
83   UNSPEC_SET_GOT
84   UNSPEC_SET_RIP
85   UNSPEC_SET_GOT_OFFSET
86   UNSPEC_MEMORY_BLOCKAGE
87   UNSPEC_STACK_CHECK
88
89   ;; TLS support
90   UNSPEC_TP
91   UNSPEC_TLS_GD
92   UNSPEC_TLS_LD_BASE
93   UNSPEC_TLSDESC
94   UNSPEC_TLS_IE_SUN
95
96   ;; Other random patterns
97   UNSPEC_SCAS
98   UNSPEC_FNSTSW
99   UNSPEC_SAHF
100   UNSPEC_PARITY
101   UNSPEC_FSTCW
102   UNSPEC_ADD_CARRY
103   UNSPEC_FLDCW
104   UNSPEC_REP
105   UNSPEC_LD_MPIC        ; load_macho_picbase
106   UNSPEC_TRUNC_NOOP
107   UNSPEC_DIV_ALREADY_SPLIT
108   UNSPEC_MS_TO_SYSV_CALL
109   UNSPEC_CALL_NEEDS_VZEROUPPER
110   UNSPEC_PAUSE
111   UNSPEC_LEA_ADDR
112
113   ;; For SSE/MMX support:
114   UNSPEC_FIX_NOTRUNC
115   UNSPEC_MASKMOV
116   UNSPEC_MOVMSK
117   UNSPEC_RCP
118   UNSPEC_RSQRT
119   UNSPEC_PSADBW
120
121   ;; Generic math support
122   UNSPEC_COPYSIGN
123   UNSPEC_IEEE_MIN       ; not commutative
124   UNSPEC_IEEE_MAX       ; not commutative
125
126   ;; x87 Floating point
127   UNSPEC_SIN
128   UNSPEC_COS
129   UNSPEC_FPATAN
130   UNSPEC_FYL2X
131   UNSPEC_FYL2XP1
132   UNSPEC_FRNDINT
133   UNSPEC_FIST
134   UNSPEC_F2XM1
135   UNSPEC_TAN
136   UNSPEC_FXAM
137
138   ;; x87 Rounding
139   UNSPEC_FRNDINT_FLOOR
140   UNSPEC_FRNDINT_CEIL
141   UNSPEC_FRNDINT_TRUNC
142   UNSPEC_FRNDINT_MASK_PM
143   UNSPEC_FIST_FLOOR
144   UNSPEC_FIST_CEIL
145
146   ;; x87 Double output FP
147   UNSPEC_SINCOS_COS
148   UNSPEC_SINCOS_SIN
149   UNSPEC_XTRACT_FRACT
150   UNSPEC_XTRACT_EXP
151   UNSPEC_FSCALE_FRACT
152   UNSPEC_FSCALE_EXP
153   UNSPEC_FPREM_F
154   UNSPEC_FPREM_U
155   UNSPEC_FPREM1_F
156   UNSPEC_FPREM1_U
157
158   UNSPEC_C2_FLAG
159   UNSPEC_FXAM_MEM
160
161   ;; SSP patterns
162   UNSPEC_SP_SET
163   UNSPEC_SP_TEST
164   UNSPEC_SP_TLS_SET
165   UNSPEC_SP_TLS_TEST
166
167   ;; For ROUND support
168   UNSPEC_ROUND
169
170   ;; For CRC32 support
171   UNSPEC_CRC32
172
173   ;; For BMI support
174   UNSPEC_BEXTR
175
176   ;; For BMI2 support
177   UNSPEC_PDEP
178   UNSPEC_PEXT
179 ])
180
181 (define_c_enum "unspecv" [
182   UNSPECV_BLOCKAGE
183   UNSPECV_STACK_PROBE
184   UNSPECV_PROBE_STACK_RANGE
185   UNSPECV_ALIGN
186   UNSPECV_PROLOGUE_USE
187   UNSPECV_SPLIT_STACK_RETURN
188   UNSPECV_CLD
189   UNSPECV_NOPS
190   UNSPECV_RDTSC
191   UNSPECV_RDTSCP
192   UNSPECV_RDPMC
193   UNSPECV_LLWP_INTRINSIC
194   UNSPECV_SLWP_INTRINSIC
195   UNSPECV_LWPVAL_INTRINSIC
196   UNSPECV_LWPINS_INTRINSIC
197   UNSPECV_RDFSBASE
198   UNSPECV_RDGSBASE
199   UNSPECV_WRFSBASE
200   UNSPECV_WRGSBASE
201
202   ;; For RDRAND support
203   UNSPECV_RDRAND
204 ])
205
206 ;; Constants to represent rounding modes in the ROUND instruction
207 (define_constants
208   [(ROUND_FLOOR                 0x1)
209    (ROUND_CEIL                  0x2)
210    (ROUND_TRUNC                 0x3)
211    (ROUND_MXCSR                 0x4)
212    (ROUND_NO_EXC                0x8)
213   ])
214
215 ;; Constants to represent pcomtrue/pcomfalse variants
216 (define_constants
217   [(PCOM_FALSE                  0)
218    (PCOM_TRUE                   1)
219    (COM_FALSE_S                 2)
220    (COM_FALSE_P                 3)
221    (COM_TRUE_S                  4)
222    (COM_TRUE_P                  5)
223   ])
224
225 ;; Constants used in the XOP pperm instruction
226 (define_constants
227   [(PPERM_SRC                   0x00)   /* copy source */
228    (PPERM_INVERT                0x20)   /* invert source */
229    (PPERM_REVERSE               0x40)   /* bit reverse source */
230    (PPERM_REV_INV               0x60)   /* bit reverse & invert src */
231    (PPERM_ZERO                  0x80)   /* all 0's */
232    (PPERM_ONES                  0xa0)   /* all 1's */
233    (PPERM_SIGN                  0xc0)   /* propagate sign bit */
234    (PPERM_INV_SIGN              0xe0)   /* invert & propagate sign */
235    (PPERM_SRC1                  0x00)   /* use first source byte */
236    (PPERM_SRC2                  0x10)   /* use second source byte */
237    ])
238
239 ;; Registers by name.
240 (define_constants
241   [(AX_REG                       0)
242    (DX_REG                       1)
243    (CX_REG                       2)
244    (BX_REG                       3)
245    (SI_REG                       4)
246    (DI_REG                       5)
247    (BP_REG                       6)
248    (SP_REG                       7)
249    (ST0_REG                      8)
250    (ST1_REG                      9)
251    (ST2_REG                     10)
252    (ST3_REG                     11)
253    (ST4_REG                     12)
254    (ST5_REG                     13)
255    (ST6_REG                     14)
256    (ST7_REG                     15)
257    (FLAGS_REG                   17)
258    (FPSR_REG                    18)
259    (FPCR_REG                    19)
260    (XMM0_REG                    21)
261    (XMM1_REG                    22)
262    (XMM2_REG                    23)
263    (XMM3_REG                    24)
264    (XMM4_REG                    25)
265    (XMM5_REG                    26)
266    (XMM6_REG                    27)
267    (XMM7_REG                    28)
268    (MM0_REG                     29)
269    (MM1_REG                     30)
270    (MM2_REG                     31)
271    (MM3_REG                     32)
272    (MM4_REG                     33)
273    (MM5_REG                     34)
274    (MM6_REG                     35)
275    (MM7_REG                     36)
276    (R8_REG                      37)
277    (R9_REG                      38)
278    (R10_REG                     39)
279    (R11_REG                     40)
280    (R12_REG                     41)
281    (R13_REG                     42)
282    (XMM8_REG                    45)
283    (XMM9_REG                    46)
284    (XMM10_REG                   47)
285    (XMM11_REG                   48)
286    (XMM12_REG                   49)
287    (XMM13_REG                   50)
288    (XMM14_REG                   51)
289    (XMM15_REG                   52)
290   ])
291
292 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
293 ;; from i386.c.
294
295 ;; In C guard expressions, put expressions which may be compile-time
296 ;; constants first.  This allows for better optimization.  For
297 ;; example, write "TARGET_64BIT && reload_completed", not
298 ;; "reload_completed && TARGET_64BIT".
299
300 \f
301 ;; Processor type.
302 (define_attr "cpu" "none,pentium,pentiumpro,geode,k6,athlon,k8,core2,corei7,
303                     atom,generic64,amdfam10,bdver1,bdver2,btver1"
304   (const (symbol_ref "ix86_schedule")))
305
306 ;; A basic instruction type.  Refinements due to arguments to be
307 ;; provided in other attributes.
308 (define_attr "type"
309   "other,multi,
310    alu,alu1,negnot,imov,imovx,lea,
311    incdec,ishift,ishiftx,ishift1,rotate,rotatex,rotate1,imul,imulx,idiv,
312    icmp,test,ibr,setcc,icmov,
313    push,pop,call,callv,leave,
314    str,bitmanip,
315    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
316    sselog,sselog1,sseiadd,sseiadd1,sseishft,sseishft1,sseimul,
317    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,ssediv,sseins,
318    ssemuladd,sse4arg,lwp,
319    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
320   (const_string "other"))
321
322 ;; Main data type used by the insn
323 (define_attr "mode"
324   "unknown,none,QI,HI,SI,DI,TI,OI,SF,DF,XF,TF,V8SF,V4DF,V4SF,V2DF,V2SF,V1DF"
325   (const_string "unknown"))
326
327 ;; The CPU unit operations uses.
328 (define_attr "unit" "integer,i387,sse,mmx,unknown"
329   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
330            (const_string "i387")
331          (eq_attr "type" "sselog,sselog1,sseiadd,sseiadd1,sseishft,sseishft1,sseimul,
332                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,
333                           ssecvt1,sseicvt,ssediv,sseins,ssemuladd,sse4arg")
334            (const_string "sse")
335          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
336            (const_string "mmx")
337          (eq_attr "type" "other")
338            (const_string "unknown")]
339          (const_string "integer")))
340
341 ;; The (bounding maximum) length of an instruction immediate.
342 (define_attr "length_immediate" ""
343   (cond [(eq_attr "type" "incdec,setcc,icmov,str,lea,other,multi,idiv,leave,
344                           bitmanip,imulx")
345            (const_int 0)
346          (eq_attr "unit" "i387,sse,mmx")
347            (const_int 0)
348          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,ishiftx,ishift1,
349                           rotate,rotatex,rotate1,imul,icmp,push,pop")
350            (symbol_ref "ix86_attr_length_immediate_default (insn, true)")
351          (eq_attr "type" "imov,test")
352            (symbol_ref "ix86_attr_length_immediate_default (insn, false)")
353          (eq_attr "type" "call")
354            (if_then_else (match_operand 0 "constant_call_address_operand" "")
355              (const_int 4)
356              (const_int 0))
357          (eq_attr "type" "callv")
358            (if_then_else (match_operand 1 "constant_call_address_operand" "")
359              (const_int 4)
360              (const_int 0))
361          ;; We don't know the size before shorten_branches.  Expect
362          ;; the instruction to fit for better scheduling.
363          (eq_attr "type" "ibr")
364            (const_int 1)
365          ]
366          (symbol_ref "/* Update immediate_length and other attributes! */
367                       gcc_unreachable (),1")))
368
369 ;; The (bounding maximum) length of an instruction address.
370 (define_attr "length_address" ""
371   (cond [(eq_attr "type" "str,other,multi,fxch")
372            (const_int 0)
373          (and (eq_attr "type" "call")
374               (match_operand 0 "constant_call_address_operand" ""))
375              (const_int 0)
376          (and (eq_attr "type" "callv")
377               (match_operand 1 "constant_call_address_operand" ""))
378              (const_int 0)
379          ]
380          (symbol_ref "ix86_attr_length_address_default (insn)")))
381
382 ;; Set when length prefix is used.
383 (define_attr "prefix_data16" ""
384   (cond [(eq_attr "type" "ssemuladd,sse4arg,sseiadd1,ssecvt1")
385            (const_int 0)
386          (eq_attr "mode" "HI")
387            (const_int 1)
388          (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF,TI"))
389            (const_int 1)
390         ]
391         (const_int 0)))
392
393 ;; Set when string REP prefix is used.
394 (define_attr "prefix_rep" ""
395   (cond [(eq_attr "type" "ssemuladd,sse4arg,sseiadd1,ssecvt1")
396            (const_int 0)
397          (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
398            (const_int 1)
399         ]
400         (const_int 0)))
401
402 ;; Set when 0f opcode prefix is used.
403 (define_attr "prefix_0f" ""
404   (if_then_else
405     (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip")
406          (eq_attr "unit" "sse,mmx"))
407     (const_int 1)
408     (const_int 0)))
409
410 ;; Set when REX opcode prefix is used.
411 (define_attr "prefix_rex" ""
412   (cond [(not (match_test "TARGET_64BIT"))
413            (const_int 0)
414          (and (eq_attr "mode" "DI")
415               (and (eq_attr "type" "!push,pop,call,callv,leave,ibr")
416                    (eq_attr "unit" "!mmx")))
417            (const_int 1)
418          (and (eq_attr "mode" "QI")
419               (match_test "x86_extended_QIreg_mentioned_p (insn)"))
420            (const_int 1)
421          (match_test "x86_extended_reg_mentioned_p (insn)")
422            (const_int 1)
423          (and (eq_attr "type" "imovx")
424               (match_operand:QI 1 "ext_QIreg_operand" ""))
425            (const_int 1)
426         ]
427         (const_int 0)))
428
429 ;; There are also additional prefixes in 3DNOW, SSSE3.
430 ;; ssemuladd,sse4arg default to 0f24/0f25 and DREX byte,
431 ;; sseiadd1,ssecvt1 to 0f7a with no DREX byte.
432 ;; 3DNOW has 0f0f prefix, SSSE3 and SSE4_{1,2} 0f38/0f3a.
433 (define_attr "prefix_extra" ""
434   (cond [(eq_attr "type" "ssemuladd,sse4arg")
435            (const_int 2)
436          (eq_attr "type" "sseiadd1,ssecvt1")
437            (const_int 1)
438         ]
439         (const_int 0)))
440
441 ;; Prefix used: original, VEX or maybe VEX.
442 (define_attr "prefix" "orig,vex,maybe_vex"
443   (if_then_else (eq_attr "mode" "OI,V8SF,V4DF")
444     (const_string "vex")
445     (const_string "orig")))
446
447 ;; VEX W bit is used.
448 (define_attr "prefix_vex_w" "" (const_int 0))
449
450 ;; The length of VEX prefix
451 ;; Only instructions with 0f prefix can have 2 byte VEX prefix,
452 ;; 0f38/0f3a prefixes can't.  In i386.md 0f3[8a] is
453 ;; still prefix_0f 1, with prefix_extra 1.
454 (define_attr "length_vex" ""
455   (if_then_else (and (eq_attr "prefix_0f" "1")
456                      (eq_attr "prefix_extra" "0"))
457     (if_then_else (eq_attr "prefix_vex_w" "1")
458       (symbol_ref "ix86_attr_length_vex_default (insn, true, true)")
459       (symbol_ref "ix86_attr_length_vex_default (insn, true, false)"))
460     (if_then_else (eq_attr "prefix_vex_w" "1")
461       (symbol_ref "ix86_attr_length_vex_default (insn, false, true)")
462       (symbol_ref "ix86_attr_length_vex_default (insn, false, false)"))))
463
464 ;; Set when modrm byte is used.
465 (define_attr "modrm" ""
466   (cond [(eq_attr "type" "str,leave")
467            (const_int 0)
468          (eq_attr "unit" "i387")
469            (const_int 0)
470          (and (eq_attr "type" "incdec")
471               (and (not (match_test "TARGET_64BIT"))
472                    (ior (match_operand:SI 1 "register_operand" "")
473                         (match_operand:HI 1 "register_operand" ""))))
474            (const_int 0)
475          (and (eq_attr "type" "push")
476               (not (match_operand 1 "memory_operand" "")))
477            (const_int 0)
478          (and (eq_attr "type" "pop")
479               (not (match_operand 0 "memory_operand" "")))
480            (const_int 0)
481          (and (eq_attr "type" "imov")
482               (and (not (eq_attr "mode" "DI"))
483                    (ior (and (match_operand 0 "register_operand" "")
484                              (match_operand 1 "immediate_operand" ""))
485                         (ior (and (match_operand 0 "ax_reg_operand" "")
486                                   (match_operand 1 "memory_displacement_only_operand" ""))
487                              (and (match_operand 0 "memory_displacement_only_operand" "")
488                                   (match_operand 1 "ax_reg_operand" ""))))))
489            (const_int 0)
490          (and (eq_attr "type" "call")
491               (match_operand 0 "constant_call_address_operand" ""))
492              (const_int 0)
493          (and (eq_attr "type" "callv")
494               (match_operand 1 "constant_call_address_operand" ""))
495              (const_int 0)
496          (and (eq_attr "type" "alu,alu1,icmp,test")
497               (match_operand 0 "ax_reg_operand" ""))
498              (symbol_ref "(get_attr_length_immediate (insn) <= (get_attr_mode (insn) != MODE_QI))")
499          ]
500          (const_int 1)))
501
502 ;; The (bounding maximum) length of an instruction in bytes.
503 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
504 ;; Later we may want to split them and compute proper length as for
505 ;; other insns.
506 (define_attr "length" ""
507   (cond [(eq_attr "type" "other,multi,fistp,frndint")
508            (const_int 16)
509          (eq_attr "type" "fcmp")
510            (const_int 4)
511          (eq_attr "unit" "i387")
512            (plus (const_int 2)
513                  (plus (attr "prefix_data16")
514                        (attr "length_address")))
515          (ior (eq_attr "prefix" "vex")
516               (and (eq_attr "prefix" "maybe_vex")
517                    (match_test "TARGET_AVX")))
518            (plus (attr "length_vex")
519                  (plus (attr "length_immediate")
520                        (plus (attr "modrm")
521                              (attr "length_address"))))]
522          (plus (plus (attr "modrm")
523                      (plus (attr "prefix_0f")
524                            (plus (attr "prefix_rex")
525                                  (plus (attr "prefix_extra")
526                                        (const_int 1)))))
527                (plus (attr "prefix_rep")
528                      (plus (attr "prefix_data16")
529                            (plus (attr "length_immediate")
530                                  (attr "length_address")))))))
531
532 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
533 ;; `store' if there is a simple memory reference therein, or `unknown'
534 ;; if the instruction is complex.
535
536 (define_attr "memory" "none,load,store,both,unknown"
537   (cond [(eq_attr "type" "other,multi,str,lwp")
538            (const_string "unknown")
539          (eq_attr "type" "lea,fcmov,fpspc")
540            (const_string "none")
541          (eq_attr "type" "fistp,leave")
542            (const_string "both")
543          (eq_attr "type" "frndint")
544            (const_string "load")
545          (eq_attr "type" "push")
546            (if_then_else (match_operand 1 "memory_operand" "")
547              (const_string "both")
548              (const_string "store"))
549          (eq_attr "type" "pop")
550            (if_then_else (match_operand 0 "memory_operand" "")
551              (const_string "both")
552              (const_string "load"))
553          (eq_attr "type" "setcc")
554            (if_then_else (match_operand 0 "memory_operand" "")
555              (const_string "store")
556              (const_string "none"))
557          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
558            (if_then_else (ior (match_operand 0 "memory_operand" "")
559                               (match_operand 1 "memory_operand" ""))
560              (const_string "load")
561              (const_string "none"))
562          (eq_attr "type" "ibr")
563            (if_then_else (match_operand 0 "memory_operand" "")
564              (const_string "load")
565              (const_string "none"))
566          (eq_attr "type" "call")
567            (if_then_else (match_operand 0 "constant_call_address_operand" "")
568              (const_string "none")
569              (const_string "load"))
570          (eq_attr "type" "callv")
571            (if_then_else (match_operand 1 "constant_call_address_operand" "")
572              (const_string "none")
573              (const_string "load"))
574          (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
575               (match_operand 1 "memory_operand" ""))
576            (const_string "both")
577          (and (match_operand 0 "memory_operand" "")
578               (match_operand 1 "memory_operand" ""))
579            (const_string "both")
580          (match_operand 0 "memory_operand" "")
581            (const_string "store")
582          (match_operand 1 "memory_operand" "")
583            (const_string "load")
584          (and (eq_attr "type"
585                  "!alu1,negnot,ishift1,
586                    imov,imovx,icmp,test,bitmanip,
587                    fmov,fcmp,fsgn,
588                    sse,ssemov,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,sselog1,
589                    sseiadd1,mmx,mmxmov,mmxcmp,mmxcvt")
590               (match_operand 2 "memory_operand" ""))
591            (const_string "load")
592          (and (eq_attr "type" "icmov,ssemuladd,sse4arg")
593               (match_operand 3 "memory_operand" ""))
594            (const_string "load")
595         ]
596         (const_string "none")))
597
598 ;; Indicates if an instruction has both an immediate and a displacement.
599
600 (define_attr "imm_disp" "false,true,unknown"
601   (cond [(eq_attr "type" "other,multi")
602            (const_string "unknown")
603          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
604               (and (match_operand 0 "memory_displacement_operand" "")
605                    (match_operand 1 "immediate_operand" "")))
606            (const_string "true")
607          (and (eq_attr "type" "alu,ishift,ishiftx,rotate,rotatex,imul,idiv")
608               (and (match_operand 0 "memory_displacement_operand" "")
609                    (match_operand 2 "immediate_operand" "")))
610            (const_string "true")
611         ]
612         (const_string "false")))
613
614 ;; Indicates if an FP operation has an integer source.
615
616 (define_attr "fp_int_src" "false,true"
617   (const_string "false"))
618
619 ;; Defines rounding mode of an FP operation.
620
621 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
622   (const_string "any"))
623
624 ;; Define attribute to classify add/sub insns that consumes carry flag (CF)
625 (define_attr "use_carry" "0,1" (const_string "0"))
626
627 ;; Define attribute to indicate unaligned ssemov insns
628 (define_attr "movu" "0,1" (const_string "0"))
629
630 ;; Used to control the "enabled" attribute on a per-instruction basis.
631 (define_attr "isa" "base,sse2,sse2_noavx,sse3,sse4,sse4_noavx,noavx,avx,bmi2"
632   (const_string "base"))
633
634 (define_attr "enabled" ""
635   (cond [(eq_attr "isa" "sse2") (symbol_ref "TARGET_SSE2")
636          (eq_attr "isa" "sse2_noavx")
637            (symbol_ref "TARGET_SSE2 && !TARGET_AVX")
638          (eq_attr "isa" "sse3") (symbol_ref "TARGET_SSE3")
639          (eq_attr "isa" "sse4") (symbol_ref "TARGET_SSE4_1")
640          (eq_attr "isa" "sse4_noavx")
641            (symbol_ref "TARGET_SSE4_1 && !TARGET_AVX")
642          (eq_attr "isa" "avx") (symbol_ref "TARGET_AVX")
643          (eq_attr "isa" "noavx") (symbol_ref "!TARGET_AVX")
644          (eq_attr "isa" "bmi2") (symbol_ref "TARGET_BMI2")
645         ]
646         (const_int 1)))
647
648 ;; Describe a user's asm statement.
649 (define_asm_attributes
650   [(set_attr "length" "128")
651    (set_attr "type" "multi")])
652
653 (define_code_iterator plusminus [plus minus])
654
655 (define_code_iterator sat_plusminus [ss_plus us_plus ss_minus us_minus])
656
657 ;; Base name for define_insn
658 (define_code_attr plusminus_insn
659   [(plus "add") (ss_plus "ssadd") (us_plus "usadd")
660    (minus "sub") (ss_minus "sssub") (us_minus "ussub")])
661
662 ;; Base name for insn mnemonic.
663 (define_code_attr plusminus_mnemonic
664   [(plus "add") (ss_plus "adds") (us_plus "addus")
665    (minus "sub") (ss_minus "subs") (us_minus "subus")])
666 (define_code_attr plusminus_carry_mnemonic
667   [(plus "adc") (minus "sbb")])
668
669 ;; Mark commutative operators as such in constraints.
670 (define_code_attr comm [(plus "%") (ss_plus "%") (us_plus "%")
671                         (minus "") (ss_minus "") (us_minus "")])
672
673 ;; Mapping of max and min
674 (define_code_iterator maxmin [smax smin umax umin])
675
676 ;; Mapping of signed max and min
677 (define_code_iterator smaxmin [smax smin])
678
679 ;; Mapping of unsigned max and min
680 (define_code_iterator umaxmin [umax umin])
681
682 ;; Base name for integer and FP insn mnemonic
683 (define_code_attr maxmin_int [(smax "maxs") (smin "mins")
684                               (umax "maxu") (umin "minu")])
685 (define_code_attr maxmin_float [(smax "max") (smin "min")])
686
687 ;; Mapping of logic operators
688 (define_code_iterator any_logic [and ior xor])
689 (define_code_iterator any_or [ior xor])
690
691 ;; Base name for insn mnemonic.
692 (define_code_attr logic [(and "and") (ior "or") (xor "xor")])
693
694 ;; Mapping of logic-shift operators
695 (define_code_iterator any_lshift [ashift lshiftrt])
696
697 ;; Mapping of shift-right operators
698 (define_code_iterator any_shiftrt [lshiftrt ashiftrt])
699
700 ;; Base name for define_insn
701 (define_code_attr shift_insn
702   [(ashift "ashl") (lshiftrt "lshr") (ashiftrt "ashr")])
703
704 ;; Base name for insn mnemonic.
705 (define_code_attr shift [(ashift "sll") (lshiftrt "shr") (ashiftrt "sar")])
706 (define_code_attr vshift [(ashift "sll") (lshiftrt "srl") (ashiftrt "sra")])
707
708 ;; Mapping of rotate operators
709 (define_code_iterator any_rotate [rotate rotatert])
710
711 ;; Base name for define_insn
712 (define_code_attr rotate_insn [(rotate "rotl") (rotatert "rotr")])
713
714 ;; Base name for insn mnemonic.
715 (define_code_attr rotate [(rotate "rol") (rotatert "ror")])
716
717 ;; Mapping of abs neg operators
718 (define_code_iterator absneg [abs neg])
719
720 ;; Base name for x87 insn mnemonic.
721 (define_code_attr absneg_mnemonic [(abs "abs") (neg "chs")])
722
723 ;; Used in signed and unsigned widening multiplications.
724 (define_code_iterator any_extend [sign_extend zero_extend])
725
726 ;; Prefix for insn menmonic.
727 (define_code_attr sgnprefix [(sign_extend "i") (zero_extend "")])
728
729 ;; Prefix for define_insn
730 (define_code_attr u [(sign_extend "") (zero_extend "u")])
731 (define_code_attr s [(sign_extend "s") (zero_extend "u")])
732
733 ;; All integer modes.
734 (define_mode_iterator SWI1248x [QI HI SI DI])
735
736 ;; All integer modes without QImode.
737 (define_mode_iterator SWI248x [HI SI DI])
738
739 ;; All integer modes without QImode and HImode.
740 (define_mode_iterator SWI48x [SI DI])
741
742 ;; All integer modes without SImode and DImode.
743 (define_mode_iterator SWI12 [QI HI])
744
745 ;; All integer modes without DImode.
746 (define_mode_iterator SWI124 [QI HI SI])
747
748 ;; All integer modes without QImode and DImode.
749 (define_mode_iterator SWI24 [HI SI])
750
751 ;; Single word integer modes.
752 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
753
754 ;; Single word integer modes without QImode.
755 (define_mode_iterator SWI248 [HI SI (DI "TARGET_64BIT")])
756
757 ;; Single word integer modes without QImode and HImode.
758 (define_mode_iterator SWI48 [SI (DI "TARGET_64BIT")])
759
760 ;; All math-dependant single and double word integer modes.
761 (define_mode_iterator SDWIM [(QI "TARGET_QIMODE_MATH")
762                              (HI "TARGET_HIMODE_MATH")
763                              SI DI (TI "TARGET_64BIT")])
764
765 ;; Math-dependant single word integer modes.
766 (define_mode_iterator SWIM [(QI "TARGET_QIMODE_MATH")
767                             (HI "TARGET_HIMODE_MATH")
768                             SI (DI "TARGET_64BIT")])
769
770 ;; Math-dependant integer modes without DImode.
771 (define_mode_iterator SWIM124 [(QI "TARGET_QIMODE_MATH")
772                                (HI "TARGET_HIMODE_MATH")
773                                SI])
774
775 ;; Math-dependant single word integer modes without QImode.
776 (define_mode_iterator SWIM248 [(HI "TARGET_HIMODE_MATH")
777                                SI (DI "TARGET_64BIT")])
778
779 ;; Double word integer modes.
780 (define_mode_iterator DWI [(DI "!TARGET_64BIT")
781                            (TI "TARGET_64BIT")])
782
783 ;; Double word integer modes as mode attribute.
784 (define_mode_attr DWI [(SI "DI") (DI "TI")])
785 (define_mode_attr dwi [(SI "di") (DI "ti")])
786
787 ;; Half mode for double word integer modes.
788 (define_mode_iterator DWIH [(SI "!TARGET_64BIT")
789                             (DI "TARGET_64BIT")])
790
791 ;; Instruction suffix for integer modes.
792 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
793
794 ;; Pointer size prefix for integer modes (Intel asm dialect)
795 (define_mode_attr iptrsize [(QI "BYTE")
796                             (HI "WORD")
797                             (SI "DWORD")
798                             (DI "QWORD")])
799
800 ;; Register class for integer modes.
801 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
802
803 ;; Immediate operand constraint for integer modes.
804 (define_mode_attr i [(QI "n") (HI "n") (SI "e") (DI "e")])
805
806 ;; General operand constraint for word modes.
807 (define_mode_attr g [(QI "qmn") (HI "rmn") (SI "rme") (DI "rme")])
808
809 ;; Immediate operand constraint for double integer modes.
810 (define_mode_attr di [(SI "nF") (DI "e")])
811
812 ;; Immediate operand constraint for shifts.
813 (define_mode_attr S [(QI "I") (HI "I") (SI "I") (DI "J") (TI "O")])
814
815 ;; General operand predicate for integer modes.
816 (define_mode_attr general_operand
817         [(QI "general_operand")
818          (HI "general_operand")
819          (SI "x86_64_general_operand")
820          (DI "x86_64_general_operand")
821          (TI "x86_64_general_operand")])
822
823 ;; General sign/zero extend operand predicate for integer modes.
824 (define_mode_attr general_szext_operand
825         [(QI "general_operand")
826          (HI "general_operand")
827          (SI "x86_64_szext_general_operand")
828          (DI "x86_64_szext_general_operand")])
829
830 ;; Immediate operand predicate for integer modes.
831 (define_mode_attr immediate_operand
832         [(QI "immediate_operand")
833          (HI "immediate_operand")
834          (SI "x86_64_immediate_operand")
835          (DI "x86_64_immediate_operand")])
836
837 ;; Nonmemory operand predicate for integer modes.
838 (define_mode_attr nonmemory_operand
839         [(QI "nonmemory_operand")
840          (HI "nonmemory_operand")
841          (SI "x86_64_nonmemory_operand")
842          (DI "x86_64_nonmemory_operand")])
843
844 ;; Operand predicate for shifts.
845 (define_mode_attr shift_operand
846         [(QI "nonimmediate_operand")
847          (HI "nonimmediate_operand")
848          (SI "nonimmediate_operand")
849          (DI "shiftdi_operand")
850          (TI "register_operand")])
851
852 ;; Operand predicate for shift argument.
853 (define_mode_attr shift_immediate_operand
854         [(QI "const_1_to_31_operand")
855          (HI "const_1_to_31_operand")
856          (SI "const_1_to_31_operand")
857          (DI "const_1_to_63_operand")])
858
859 ;; Input operand predicate for arithmetic left shifts.
860 (define_mode_attr ashl_input_operand
861         [(QI "nonimmediate_operand")
862          (HI "nonimmediate_operand")
863          (SI "nonimmediate_operand")
864          (DI "ashldi_input_operand")
865          (TI "reg_or_pm1_operand")])
866
867 ;; SSE and x87 SFmode and DFmode floating point modes
868 (define_mode_iterator MODEF [SF DF])
869
870 ;; All x87 floating point modes
871 (define_mode_iterator X87MODEF [SF DF XF])
872
873 ;; SSE instruction suffix for various modes
874 (define_mode_attr ssemodesuffix
875   [(SF "ss") (DF "sd")
876    (V8SF "ps") (V4DF "pd")
877    (V4SF "ps") (V2DF "pd")
878    (V16QI "b") (V8HI "w") (V4SI "d") (V2DI "q")
879    (V32QI "b") (V16HI "w") (V8SI "d") (V4DI "q")])
880
881 ;; SSE vector suffix for floating point modes
882 (define_mode_attr ssevecmodesuffix [(SF "ps") (DF "pd")])
883
884 ;; SSE vector mode corresponding to a scalar mode
885 (define_mode_attr ssevecmode
886   [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
887
888 ;; Instruction suffix for REX 64bit operators.
889 (define_mode_attr rex64suffix [(SI "") (DI "{q}")])
890
891 ;; This mode iterator allows :P to be used for patterns that operate on
892 ;; pointer-sized quantities.  Exactly one of the two alternatives will match.
893 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
894
895 ;; This mode iterator allows :PTR to be used for patterns that operate on
896 ;; ptr_mode sized quantities.
897 (define_mode_iterator PTR
898   [(SI "ptr_mode == SImode") (DI "ptr_mode == DImode")])
899 \f
900 ;; Scheduling descriptions
901
902 (include "pentium.md")
903 (include "ppro.md")
904 (include "k6.md")
905 (include "athlon.md")
906 (include "bdver1.md")
907 (include "geode.md")
908 (include "atom.md")
909 (include "core2.md")
910
911 \f
912 ;; Operand and operator predicates and constraints
913
914 (include "predicates.md")
915 (include "constraints.md")
916
917 \f
918 ;; Compare and branch/compare and store instructions.
919
920 (define_expand "cbranch<mode>4"
921   [(set (reg:CC FLAGS_REG)
922         (compare:CC (match_operand:SDWIM 1 "nonimmediate_operand" "")
923                     (match_operand:SDWIM 2 "<general_operand>" "")))
924    (set (pc) (if_then_else
925                (match_operator 0 "ordered_comparison_operator"
926                 [(reg:CC FLAGS_REG) (const_int 0)])
927                (label_ref (match_operand 3 "" ""))
928                (pc)))]
929   ""
930 {
931   if (MEM_P (operands[1]) && MEM_P (operands[2]))
932     operands[1] = force_reg (<MODE>mode, operands[1]);
933   ix86_expand_branch (GET_CODE (operands[0]),
934                       operands[1], operands[2], operands[3]);
935   DONE;
936 })
937
938 (define_expand "cstore<mode>4"
939   [(set (reg:CC FLAGS_REG)
940         (compare:CC (match_operand:SWIM 2 "nonimmediate_operand" "")
941                     (match_operand:SWIM 3 "<general_operand>" "")))
942    (set (match_operand:QI 0 "register_operand" "")
943         (match_operator 1 "ordered_comparison_operator"
944           [(reg:CC FLAGS_REG) (const_int 0)]))]
945   ""
946 {
947   if (MEM_P (operands[2]) && MEM_P (operands[3]))
948     operands[2] = force_reg (<MODE>mode, operands[2]);
949   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
950                      operands[2], operands[3]);
951   DONE;
952 })
953
954 (define_expand "cmp<mode>_1"
955   [(set (reg:CC FLAGS_REG)
956         (compare:CC (match_operand:SWI48 0 "nonimmediate_operand" "")
957                     (match_operand:SWI48 1 "<general_operand>" "")))])
958
959 (define_insn "*cmp<mode>_ccno_1"
960   [(set (reg FLAGS_REG)
961         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>,?m<r>")
962                  (match_operand:SWI 1 "const0_operand" "")))]
963   "ix86_match_ccmode (insn, CCNOmode)"
964   "@
965    test{<imodesuffix>}\t%0, %0
966    cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
967   [(set_attr "type" "test,icmp")
968    (set_attr "length_immediate" "0,1")
969    (set_attr "mode" "<MODE>")])
970
971 (define_insn "*cmp<mode>_1"
972   [(set (reg FLAGS_REG)
973         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
974                  (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m")))]
975   "ix86_match_ccmode (insn, CCmode)"
976   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
977   [(set_attr "type" "icmp")
978    (set_attr "mode" "<MODE>")])
979
980 (define_insn "*cmp<mode>_minus_1"
981   [(set (reg FLAGS_REG)
982         (compare
983           (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
984                      (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
985           (const_int 0)))]
986   "ix86_match_ccmode (insn, CCGOCmode)"
987   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
988   [(set_attr "type" "icmp")
989    (set_attr "mode" "<MODE>")])
990
991 (define_insn "*cmpqi_ext_1"
992   [(set (reg FLAGS_REG)
993         (compare
994           (match_operand:QI 0 "general_operand" "Qm")
995           (subreg:QI
996             (zero_extract:SI
997               (match_operand 1 "ext_register_operand" "Q")
998               (const_int 8)
999               (const_int 8)) 0)))]
1000   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1001   "cmp{b}\t{%h1, %0|%0, %h1}"
1002   [(set_attr "type" "icmp")
1003    (set_attr "mode" "QI")])
1004
1005 (define_insn "*cmpqi_ext_1_rex64"
1006   [(set (reg FLAGS_REG)
1007         (compare
1008           (match_operand:QI 0 "register_operand" "Q")
1009           (subreg:QI
1010             (zero_extract:SI
1011               (match_operand 1 "ext_register_operand" "Q")
1012               (const_int 8)
1013               (const_int 8)) 0)))]
1014   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1015   "cmp{b}\t{%h1, %0|%0, %h1}"
1016   [(set_attr "type" "icmp")
1017    (set_attr "mode" "QI")])
1018
1019 (define_insn "*cmpqi_ext_2"
1020   [(set (reg FLAGS_REG)
1021         (compare
1022           (subreg:QI
1023             (zero_extract:SI
1024               (match_operand 0 "ext_register_operand" "Q")
1025               (const_int 8)
1026               (const_int 8)) 0)
1027           (match_operand:QI 1 "const0_operand" "")))]
1028   "ix86_match_ccmode (insn, CCNOmode)"
1029   "test{b}\t%h0, %h0"
1030   [(set_attr "type" "test")
1031    (set_attr "length_immediate" "0")
1032    (set_attr "mode" "QI")])
1033
1034 (define_expand "cmpqi_ext_3"
1035   [(set (reg:CC FLAGS_REG)
1036         (compare:CC
1037           (subreg:QI
1038             (zero_extract:SI
1039               (match_operand 0 "ext_register_operand" "")
1040               (const_int 8)
1041               (const_int 8)) 0)
1042           (match_operand:QI 1 "immediate_operand" "")))])
1043
1044 (define_insn "*cmpqi_ext_3_insn"
1045   [(set (reg FLAGS_REG)
1046         (compare
1047           (subreg:QI
1048             (zero_extract:SI
1049               (match_operand 0 "ext_register_operand" "Q")
1050               (const_int 8)
1051               (const_int 8)) 0)
1052           (match_operand:QI 1 "general_operand" "Qmn")))]
1053   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1054   "cmp{b}\t{%1, %h0|%h0, %1}"
1055   [(set_attr "type" "icmp")
1056    (set_attr "modrm" "1")
1057    (set_attr "mode" "QI")])
1058
1059 (define_insn "*cmpqi_ext_3_insn_rex64"
1060   [(set (reg FLAGS_REG)
1061         (compare
1062           (subreg:QI
1063             (zero_extract:SI
1064               (match_operand 0 "ext_register_operand" "Q")
1065               (const_int 8)
1066               (const_int 8)) 0)
1067           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
1068   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1069   "cmp{b}\t{%1, %h0|%h0, %1}"
1070   [(set_attr "type" "icmp")
1071    (set_attr "modrm" "1")
1072    (set_attr "mode" "QI")])
1073
1074 (define_insn "*cmpqi_ext_4"
1075   [(set (reg FLAGS_REG)
1076         (compare
1077           (subreg:QI
1078             (zero_extract:SI
1079               (match_operand 0 "ext_register_operand" "Q")
1080               (const_int 8)
1081               (const_int 8)) 0)
1082           (subreg:QI
1083             (zero_extract:SI
1084               (match_operand 1 "ext_register_operand" "Q")
1085               (const_int 8)
1086               (const_int 8)) 0)))]
1087   "ix86_match_ccmode (insn, CCmode)"
1088   "cmp{b}\t{%h1, %h0|%h0, %h1}"
1089   [(set_attr "type" "icmp")
1090    (set_attr "mode" "QI")])
1091
1092 ;; These implement float point compares.
1093 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
1094 ;; which would allow mix and match FP modes on the compares.  Which is what
1095 ;; the old patterns did, but with many more of them.
1096
1097 (define_expand "cbranchxf4"
1098   [(set (reg:CC FLAGS_REG)
1099         (compare:CC (match_operand:XF 1 "nonmemory_operand" "")
1100                     (match_operand:XF 2 "nonmemory_operand" "")))
1101    (set (pc) (if_then_else
1102               (match_operator 0 "ix86_fp_comparison_operator"
1103                [(reg:CC FLAGS_REG)
1104                 (const_int 0)])
1105               (label_ref (match_operand 3 "" ""))
1106               (pc)))]
1107   "TARGET_80387"
1108 {
1109   ix86_expand_branch (GET_CODE (operands[0]),
1110                       operands[1], operands[2], operands[3]);
1111   DONE;
1112 })
1113
1114 (define_expand "cstorexf4"
1115   [(set (reg:CC FLAGS_REG)
1116         (compare:CC (match_operand:XF 2 "nonmemory_operand" "")
1117                     (match_operand:XF 3 "nonmemory_operand" "")))
1118    (set (match_operand:QI 0 "register_operand" "")
1119               (match_operator 1 "ix86_fp_comparison_operator"
1120                [(reg:CC FLAGS_REG)
1121                 (const_int 0)]))]
1122   "TARGET_80387"
1123 {
1124   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1125                      operands[2], operands[3]);
1126   DONE;
1127 })
1128
1129 (define_expand "cbranch<mode>4"
1130   [(set (reg:CC FLAGS_REG)
1131         (compare:CC (match_operand:MODEF 1 "cmp_fp_expander_operand" "")
1132                     (match_operand:MODEF 2 "cmp_fp_expander_operand" "")))
1133    (set (pc) (if_then_else
1134               (match_operator 0 "ix86_fp_comparison_operator"
1135                [(reg:CC FLAGS_REG)
1136                 (const_int 0)])
1137               (label_ref (match_operand 3 "" ""))
1138               (pc)))]
1139   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1140 {
1141   ix86_expand_branch (GET_CODE (operands[0]),
1142                       operands[1], operands[2], operands[3]);
1143   DONE;
1144 })
1145
1146 (define_expand "cstore<mode>4"
1147   [(set (reg:CC FLAGS_REG)
1148         (compare:CC (match_operand:MODEF 2 "cmp_fp_expander_operand" "")
1149                     (match_operand:MODEF 3 "cmp_fp_expander_operand" "")))
1150    (set (match_operand:QI 0 "register_operand" "")
1151               (match_operator 1 "ix86_fp_comparison_operator"
1152                [(reg:CC FLAGS_REG)
1153                 (const_int 0)]))]
1154   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1155 {
1156   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1157                      operands[2], operands[3]);
1158   DONE;
1159 })
1160
1161 (define_expand "cbranchcc4"
1162   [(set (pc) (if_then_else
1163               (match_operator 0 "comparison_operator"
1164                [(match_operand 1 "flags_reg_operand" "")
1165                 (match_operand 2 "const0_operand" "")])
1166               (label_ref (match_operand 3 "" ""))
1167               (pc)))]
1168   ""
1169 {
1170   ix86_expand_branch (GET_CODE (operands[0]),
1171                       operands[1], operands[2], operands[3]);
1172   DONE;
1173 })
1174
1175 (define_expand "cstorecc4"
1176   [(set (match_operand:QI 0 "register_operand" "")
1177               (match_operator 1 "comparison_operator"
1178                [(match_operand 2 "flags_reg_operand" "")
1179                 (match_operand 3 "const0_operand" "")]))]
1180   ""
1181 {
1182   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1183                      operands[2], operands[3]);
1184   DONE;
1185 })
1186
1187
1188 ;; FP compares, step 1:
1189 ;; Set the FP condition codes.
1190 ;;
1191 ;; CCFPmode     compare with exceptions
1192 ;; CCFPUmode    compare with no exceptions
1193
1194 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1195 ;; used to manage the reg stack popping would not be preserved.
1196
1197 (define_insn "*cmpfp_0"
1198   [(set (match_operand:HI 0 "register_operand" "=a")
1199         (unspec:HI
1200           [(compare:CCFP
1201              (match_operand 1 "register_operand" "f")
1202              (match_operand 2 "const0_operand" ""))]
1203         UNSPEC_FNSTSW))]
1204   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1205    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1206   "* return output_fp_compare (insn, operands, false, false);"
1207   [(set_attr "type" "multi")
1208    (set_attr "unit" "i387")
1209    (set (attr "mode")
1210      (cond [(match_operand:SF 1 "" "")
1211               (const_string "SF")
1212             (match_operand:DF 1 "" "")
1213               (const_string "DF")
1214            ]
1215            (const_string "XF")))])
1216
1217 (define_insn_and_split "*cmpfp_0_cc"
1218   [(set (reg:CCFP FLAGS_REG)
1219         (compare:CCFP
1220           (match_operand 1 "register_operand" "f")
1221           (match_operand 2 "const0_operand" "")))
1222    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1223   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1224    && TARGET_SAHF && !TARGET_CMOVE
1225    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1226   "#"
1227   "&& reload_completed"
1228   [(set (match_dup 0)
1229         (unspec:HI
1230           [(compare:CCFP (match_dup 1)(match_dup 2))]
1231         UNSPEC_FNSTSW))
1232    (set (reg:CC FLAGS_REG)
1233         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1234   ""
1235   [(set_attr "type" "multi")
1236    (set_attr "unit" "i387")
1237    (set (attr "mode")
1238      (cond [(match_operand:SF 1 "" "")
1239               (const_string "SF")
1240             (match_operand:DF 1 "" "")
1241               (const_string "DF")
1242            ]
1243            (const_string "XF")))])
1244
1245 (define_insn "*cmpfp_xf"
1246   [(set (match_operand:HI 0 "register_operand" "=a")
1247         (unspec:HI
1248           [(compare:CCFP
1249              (match_operand:XF 1 "register_operand" "f")
1250              (match_operand:XF 2 "register_operand" "f"))]
1251           UNSPEC_FNSTSW))]
1252   "TARGET_80387"
1253   "* return output_fp_compare (insn, operands, false, false);"
1254   [(set_attr "type" "multi")
1255    (set_attr "unit" "i387")
1256    (set_attr "mode" "XF")])
1257
1258 (define_insn_and_split "*cmpfp_xf_cc"
1259   [(set (reg:CCFP FLAGS_REG)
1260         (compare:CCFP
1261           (match_operand:XF 1 "register_operand" "f")
1262           (match_operand:XF 2 "register_operand" "f")))
1263    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1264   "TARGET_80387
1265    && TARGET_SAHF && !TARGET_CMOVE"
1266   "#"
1267   "&& reload_completed"
1268   [(set (match_dup 0)
1269         (unspec:HI
1270           [(compare:CCFP (match_dup 1)(match_dup 2))]
1271         UNSPEC_FNSTSW))
1272    (set (reg:CC FLAGS_REG)
1273         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1274   ""
1275   [(set_attr "type" "multi")
1276    (set_attr "unit" "i387")
1277    (set_attr "mode" "XF")])
1278
1279 (define_insn "*cmpfp_<mode>"
1280   [(set (match_operand:HI 0 "register_operand" "=a")
1281         (unspec:HI
1282           [(compare:CCFP
1283              (match_operand:MODEF 1 "register_operand" "f")
1284              (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1285           UNSPEC_FNSTSW))]
1286   "TARGET_80387"
1287   "* return output_fp_compare (insn, operands, false, false);"
1288   [(set_attr "type" "multi")
1289    (set_attr "unit" "i387")
1290    (set_attr "mode" "<MODE>")])
1291
1292 (define_insn_and_split "*cmpfp_<mode>_cc"
1293   [(set (reg:CCFP FLAGS_REG)
1294         (compare:CCFP
1295           (match_operand:MODEF 1 "register_operand" "f")
1296           (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1297    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1298   "TARGET_80387
1299    && TARGET_SAHF && !TARGET_CMOVE"
1300   "#"
1301   "&& reload_completed"
1302   [(set (match_dup 0)
1303         (unspec:HI
1304           [(compare:CCFP (match_dup 1)(match_dup 2))]
1305         UNSPEC_FNSTSW))
1306    (set (reg:CC FLAGS_REG)
1307         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1308   ""
1309   [(set_attr "type" "multi")
1310    (set_attr "unit" "i387")
1311    (set_attr "mode" "<MODE>")])
1312
1313 (define_insn "*cmpfp_u"
1314   [(set (match_operand:HI 0 "register_operand" "=a")
1315         (unspec:HI
1316           [(compare:CCFPU
1317              (match_operand 1 "register_operand" "f")
1318              (match_operand 2 "register_operand" "f"))]
1319           UNSPEC_FNSTSW))]
1320   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1321    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1322   "* return output_fp_compare (insn, operands, false, true);"
1323   [(set_attr "type" "multi")
1324    (set_attr "unit" "i387")
1325    (set (attr "mode")
1326      (cond [(match_operand:SF 1 "" "")
1327               (const_string "SF")
1328             (match_operand:DF 1 "" "")
1329               (const_string "DF")
1330            ]
1331            (const_string "XF")))])
1332
1333 (define_insn_and_split "*cmpfp_u_cc"
1334   [(set (reg:CCFPU FLAGS_REG)
1335         (compare:CCFPU
1336           (match_operand 1 "register_operand" "f")
1337           (match_operand 2 "register_operand" "f")))
1338    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1339   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1340    && TARGET_SAHF && !TARGET_CMOVE
1341    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1342   "#"
1343   "&& reload_completed"
1344   [(set (match_dup 0)
1345         (unspec:HI
1346           [(compare:CCFPU (match_dup 1)(match_dup 2))]
1347         UNSPEC_FNSTSW))
1348    (set (reg:CC FLAGS_REG)
1349         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1350   ""
1351   [(set_attr "type" "multi")
1352    (set_attr "unit" "i387")
1353    (set (attr "mode")
1354      (cond [(match_operand:SF 1 "" "")
1355               (const_string "SF")
1356             (match_operand:DF 1 "" "")
1357               (const_string "DF")
1358            ]
1359            (const_string "XF")))])
1360
1361 (define_insn "*cmpfp_<mode>"
1362   [(set (match_operand:HI 0 "register_operand" "=a")
1363         (unspec:HI
1364           [(compare:CCFP
1365              (match_operand 1 "register_operand" "f")
1366              (match_operator 3 "float_operator"
1367                [(match_operand:SWI24 2 "memory_operand" "m")]))]
1368           UNSPEC_FNSTSW))]
1369   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1370    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1371    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1372   "* return output_fp_compare (insn, operands, false, false);"
1373   [(set_attr "type" "multi")
1374    (set_attr "unit" "i387")
1375    (set_attr "fp_int_src" "true")
1376    (set_attr "mode" "<MODE>")])
1377
1378 (define_insn_and_split "*cmpfp_<mode>_cc"
1379   [(set (reg:CCFP FLAGS_REG)
1380         (compare:CCFP
1381           (match_operand 1 "register_operand" "f")
1382           (match_operator 3 "float_operator"
1383             [(match_operand:SWI24 2 "memory_operand" "m")])))
1384    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1385   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1386    && TARGET_SAHF && !TARGET_CMOVE
1387    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1388    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1389   "#"
1390   "&& reload_completed"
1391   [(set (match_dup 0)
1392         (unspec:HI
1393           [(compare:CCFP
1394              (match_dup 1)
1395              (match_op_dup 3 [(match_dup 2)]))]
1396         UNSPEC_FNSTSW))
1397    (set (reg:CC FLAGS_REG)
1398         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1399   ""
1400   [(set_attr "type" "multi")
1401    (set_attr "unit" "i387")
1402    (set_attr "fp_int_src" "true")
1403    (set_attr "mode" "<MODE>")])
1404
1405 ;; FP compares, step 2
1406 ;; Move the fpsw to ax.
1407
1408 (define_insn "x86_fnstsw_1"
1409   [(set (match_operand:HI 0 "register_operand" "=a")
1410         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1411   "TARGET_80387"
1412   "fnstsw\t%0"
1413   [(set (attr "length")
1414         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
1415    (set_attr "mode" "SI")
1416    (set_attr "unit" "i387")])
1417
1418 ;; FP compares, step 3
1419 ;; Get ax into flags, general case.
1420
1421 (define_insn "x86_sahf_1"
1422   [(set (reg:CC FLAGS_REG)
1423         (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1424                    UNSPEC_SAHF))]
1425   "TARGET_SAHF"
1426 {
1427 #ifndef HAVE_AS_IX86_SAHF
1428   if (TARGET_64BIT)
1429     return ASM_BYTE "0x9e";
1430   else
1431 #endif
1432   return "sahf";
1433 }
1434   [(set_attr "length" "1")
1435    (set_attr "athlon_decode" "vector")
1436    (set_attr "amdfam10_decode" "direct")
1437    (set_attr "bdver1_decode" "direct")
1438    (set_attr "mode" "SI")])
1439
1440 ;; Pentium Pro can do steps 1 through 3 in one go.
1441 ;; comi*, ucomi*, fcomi*, ficomi*, fucomi*
1442 ;; (these i387 instructions set flags directly)
1443 (define_insn "*cmpfp_i_mixed"
1444   [(set (reg:CCFP FLAGS_REG)
1445         (compare:CCFP (match_operand 0 "register_operand" "f,x")
1446                       (match_operand 1 "nonimmediate_operand" "f,xm")))]
1447   "TARGET_MIX_SSE_I387
1448    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1449    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1450   "* return output_fp_compare (insn, operands, true, false);"
1451   [(set_attr "type" "fcmp,ssecomi")
1452    (set_attr "prefix" "orig,maybe_vex")
1453    (set (attr "mode")
1454      (if_then_else (match_operand:SF 1 "" "")
1455         (const_string "SF")
1456         (const_string "DF")))
1457    (set (attr "prefix_rep")
1458         (if_then_else (eq_attr "type" "ssecomi")
1459                       (const_string "0")
1460                       (const_string "*")))
1461    (set (attr "prefix_data16")
1462         (cond [(eq_attr "type" "fcmp")
1463                  (const_string "*")
1464                (eq_attr "mode" "DF")
1465                  (const_string "1")
1466               ]
1467               (const_string "0")))
1468    (set_attr "athlon_decode" "vector")
1469    (set_attr "amdfam10_decode" "direct")
1470    (set_attr "bdver1_decode" "double")])
1471
1472 (define_insn "*cmpfp_i_sse"
1473   [(set (reg:CCFP FLAGS_REG)
1474         (compare:CCFP (match_operand 0 "register_operand" "x")
1475                       (match_operand 1 "nonimmediate_operand" "xm")))]
1476   "TARGET_SSE_MATH
1477    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1478    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1479   "* return output_fp_compare (insn, operands, true, false);"
1480   [(set_attr "type" "ssecomi")
1481    (set_attr "prefix" "maybe_vex")
1482    (set (attr "mode")
1483      (if_then_else (match_operand:SF 1 "" "")
1484         (const_string "SF")
1485         (const_string "DF")))
1486    (set_attr "prefix_rep" "0")
1487    (set (attr "prefix_data16")
1488         (if_then_else (eq_attr "mode" "DF")
1489                       (const_string "1")
1490                       (const_string "0")))
1491    (set_attr "athlon_decode" "vector")
1492    (set_attr "amdfam10_decode" "direct")
1493    (set_attr "bdver1_decode" "double")])
1494
1495 (define_insn "*cmpfp_i_i387"
1496   [(set (reg:CCFP FLAGS_REG)
1497         (compare:CCFP (match_operand 0 "register_operand" "f")
1498                       (match_operand 1 "register_operand" "f")))]
1499   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1500    && TARGET_CMOVE
1501    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1502    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1503   "* return output_fp_compare (insn, operands, true, false);"
1504   [(set_attr "type" "fcmp")
1505    (set (attr "mode")
1506      (cond [(match_operand:SF 1 "" "")
1507               (const_string "SF")
1508             (match_operand:DF 1 "" "")
1509               (const_string "DF")
1510            ]
1511            (const_string "XF")))
1512    (set_attr "athlon_decode" "vector")
1513    (set_attr "amdfam10_decode" "direct")
1514    (set_attr "bdver1_decode" "double")])
1515
1516 (define_insn "*cmpfp_iu_mixed"
1517   [(set (reg:CCFPU FLAGS_REG)
1518         (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1519                        (match_operand 1 "nonimmediate_operand" "f,xm")))]
1520   "TARGET_MIX_SSE_I387
1521    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1522    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1523   "* return output_fp_compare (insn, operands, true, true);"
1524   [(set_attr "type" "fcmp,ssecomi")
1525    (set_attr "prefix" "orig,maybe_vex")
1526    (set (attr "mode")
1527      (if_then_else (match_operand:SF 1 "" "")
1528         (const_string "SF")
1529         (const_string "DF")))
1530    (set (attr "prefix_rep")
1531         (if_then_else (eq_attr "type" "ssecomi")
1532                       (const_string "0")
1533                       (const_string "*")))
1534    (set (attr "prefix_data16")
1535         (cond [(eq_attr "type" "fcmp")
1536                  (const_string "*")
1537                (eq_attr "mode" "DF")
1538                  (const_string "1")
1539               ]
1540               (const_string "0")))
1541    (set_attr "athlon_decode" "vector")
1542    (set_attr "amdfam10_decode" "direct")
1543    (set_attr "bdver1_decode" "double")])
1544
1545 (define_insn "*cmpfp_iu_sse"
1546   [(set (reg:CCFPU FLAGS_REG)
1547         (compare:CCFPU (match_operand 0 "register_operand" "x")
1548                        (match_operand 1 "nonimmediate_operand" "xm")))]
1549   "TARGET_SSE_MATH
1550    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1551    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1552   "* return output_fp_compare (insn, operands, true, true);"
1553   [(set_attr "type" "ssecomi")
1554    (set_attr "prefix" "maybe_vex")
1555    (set (attr "mode")
1556      (if_then_else (match_operand:SF 1 "" "")
1557         (const_string "SF")
1558         (const_string "DF")))
1559    (set_attr "prefix_rep" "0")
1560    (set (attr "prefix_data16")
1561         (if_then_else (eq_attr "mode" "DF")
1562                       (const_string "1")
1563                       (const_string "0")))
1564    (set_attr "athlon_decode" "vector")
1565    (set_attr "amdfam10_decode" "direct")
1566    (set_attr "bdver1_decode" "double")])
1567
1568 (define_insn "*cmpfp_iu_387"
1569   [(set (reg:CCFPU FLAGS_REG)
1570         (compare:CCFPU (match_operand 0 "register_operand" "f")
1571                        (match_operand 1 "register_operand" "f")))]
1572   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1573    && TARGET_CMOVE
1574    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1575    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1576   "* return output_fp_compare (insn, operands, true, true);"
1577   [(set_attr "type" "fcmp")
1578    (set (attr "mode")
1579      (cond [(match_operand:SF 1 "" "")
1580               (const_string "SF")
1581             (match_operand:DF 1 "" "")
1582               (const_string "DF")
1583            ]
1584            (const_string "XF")))
1585    (set_attr "athlon_decode" "vector")
1586    (set_attr "amdfam10_decode" "direct")
1587    (set_attr "bdver1_decode" "direct")])
1588 \f
1589 ;; Push/pop instructions.
1590
1591 (define_insn "*push<mode>2"
1592   [(set (match_operand:DWI 0 "push_operand" "=<")
1593         (match_operand:DWI 1 "general_no_elim_operand" "riF*o"))]
1594   ""
1595   "#"
1596   [(set_attr "type" "multi")
1597    (set_attr "mode" "<MODE>")])
1598
1599 (define_split
1600   [(set (match_operand:TI 0 "push_operand" "")
1601         (match_operand:TI 1 "general_operand" ""))]
1602   "TARGET_64BIT && reload_completed
1603    && !SSE_REG_P (operands[1])"
1604   [(const_int 0)]
1605   "ix86_split_long_move (operands); DONE;")
1606
1607 (define_insn "*pushdi2_rex64"
1608   [(set (match_operand:DI 0 "push_operand" "=<,!<")
1609         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1610   "TARGET_64BIT"
1611   "@
1612    push{q}\t%1
1613    #"
1614   [(set_attr "type" "push,multi")
1615    (set_attr "mode" "DI")])
1616
1617 ;; Convert impossible pushes of immediate to existing instructions.
1618 ;; First try to get scratch register and go through it.  In case this
1619 ;; fails, push sign extended lower part first and then overwrite
1620 ;; upper part by 32bit move.
1621 (define_peephole2
1622   [(match_scratch:DI 2 "r")
1623    (set (match_operand:DI 0 "push_operand" "")
1624         (match_operand:DI 1 "immediate_operand" ""))]
1625   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1626    && !x86_64_immediate_operand (operands[1], DImode)"
1627   [(set (match_dup 2) (match_dup 1))
1628    (set (match_dup 0) (match_dup 2))])
1629
1630 ;; We need to define this as both peepholer and splitter for case
1631 ;; peephole2 pass is not run.
1632 ;; "&& 1" is needed to keep it from matching the previous pattern.
1633 (define_peephole2
1634   [(set (match_operand:DI 0 "push_operand" "")
1635         (match_operand:DI 1 "immediate_operand" ""))]
1636   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1637    && !x86_64_immediate_operand (operands[1], DImode) && 1"
1638   [(set (match_dup 0) (match_dup 1))
1639    (set (match_dup 2) (match_dup 3))]
1640 {
1641   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1642
1643   operands[1] = gen_lowpart (DImode, operands[2]);
1644   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1645                                                    GEN_INT (4)));
1646 })
1647
1648 (define_split
1649   [(set (match_operand:DI 0 "push_operand" "")
1650         (match_operand:DI 1 "immediate_operand" ""))]
1651   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1652                     ? epilogue_completed : reload_completed)
1653    && !symbolic_operand (operands[1], DImode)
1654    && !x86_64_immediate_operand (operands[1], DImode)"
1655   [(set (match_dup 0) (match_dup 1))
1656    (set (match_dup 2) (match_dup 3))]
1657 {
1658   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1659
1660   operands[1] = gen_lowpart (DImode, operands[2]);
1661   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1662                                                    GEN_INT (4)));
1663 })
1664
1665 (define_split
1666   [(set (match_operand:DI 0 "push_operand" "")
1667         (match_operand:DI 1 "general_operand" ""))]
1668   "!TARGET_64BIT && reload_completed
1669    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
1670   [(const_int 0)]
1671   "ix86_split_long_move (operands); DONE;")
1672
1673 (define_insn "*pushsi2"
1674   [(set (match_operand:SI 0 "push_operand" "=<")
1675         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1676   "!TARGET_64BIT"
1677   "push{l}\t%1"
1678   [(set_attr "type" "push")
1679    (set_attr "mode" "SI")])
1680
1681 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1682 ;; "push a byte/word".  But actually we use pushl, which has the effect
1683 ;; of rounding the amount pushed up to a word.
1684
1685 ;; For TARGET_64BIT we always round up to 8 bytes.
1686 (define_insn "*push<mode>2_rex64"
1687   [(set (match_operand:SWI124 0 "push_operand" "=X")
1688         (match_operand:SWI124 1 "nonmemory_no_elim_operand" "r<i>"))]
1689   "TARGET_64BIT"
1690   "push{q}\t%q1"
1691   [(set_attr "type" "push")
1692    (set_attr "mode" "DI")])
1693
1694 (define_insn "*push<mode>2"
1695   [(set (match_operand:SWI12 0 "push_operand" "=X")
1696         (match_operand:SWI12 1 "nonmemory_no_elim_operand" "rn"))]
1697   "!TARGET_64BIT"
1698   "push{l}\t%k1"
1699   [(set_attr "type" "push")
1700    (set_attr "mode" "SI")])
1701
1702 (define_insn "*push<mode>2_prologue"
1703   [(set (match_operand:P 0 "push_operand" "=<")
1704         (match_operand:P 1 "general_no_elim_operand" "r<i>*m"))
1705    (clobber (mem:BLK (scratch)))]
1706   ""
1707   "push{<imodesuffix>}\t%1"
1708   [(set_attr "type" "push")
1709    (set_attr "mode" "<MODE>")])
1710
1711 (define_insn "*pop<mode>1"
1712   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1713         (match_operand:P 1 "pop_operand" ">"))]
1714   ""
1715   "pop{<imodesuffix>}\t%0"
1716   [(set_attr "type" "pop")
1717    (set_attr "mode" "<MODE>")])
1718
1719 (define_insn "*pop<mode>1_epilogue"
1720   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1721         (match_operand:P 1 "pop_operand" ">"))
1722    (clobber (mem:BLK (scratch)))]
1723   ""
1724   "pop{<imodesuffix>}\t%0"
1725   [(set_attr "type" "pop")
1726    (set_attr "mode" "<MODE>")])
1727 \f
1728 ;; Move instructions.
1729
1730 (define_expand "movoi"
1731   [(set (match_operand:OI 0 "nonimmediate_operand" "")
1732         (match_operand:OI 1 "general_operand" ""))]
1733   "TARGET_AVX"
1734   "ix86_expand_move (OImode, operands); DONE;")
1735
1736 (define_expand "movti"
1737   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1738         (match_operand:TI 1 "nonimmediate_operand" ""))]
1739   "TARGET_64BIT || TARGET_SSE"
1740 {
1741   if (TARGET_64BIT)
1742     ix86_expand_move (TImode, operands);
1743   else if (push_operand (operands[0], TImode))
1744     ix86_expand_push (TImode, operands[1]);
1745   else
1746     ix86_expand_vector_move (TImode, operands);
1747   DONE;
1748 })
1749
1750 ;; This expands to what emit_move_complex would generate if we didn't
1751 ;; have a movti pattern.  Having this avoids problems with reload on
1752 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
1753 ;; to have around all the time.
1754 (define_expand "movcdi"
1755   [(set (match_operand:CDI 0 "nonimmediate_operand" "")
1756         (match_operand:CDI 1 "general_operand" ""))]
1757   ""
1758 {
1759   if (push_operand (operands[0], CDImode))
1760     emit_move_complex_push (CDImode, operands[0], operands[1]);
1761   else
1762     emit_move_complex_parts (operands[0], operands[1]);
1763   DONE;
1764 })
1765
1766 (define_expand "mov<mode>"
1767   [(set (match_operand:SWI1248x 0 "nonimmediate_operand" "")
1768         (match_operand:SWI1248x 1 "general_operand" ""))]
1769   ""
1770   "ix86_expand_move (<MODE>mode, operands); DONE;")
1771
1772 (define_insn "*mov<mode>_xor"
1773   [(set (match_operand:SWI48 0 "register_operand" "=r")
1774         (match_operand:SWI48 1 "const0_operand" ""))
1775    (clobber (reg:CC FLAGS_REG))]
1776   "reload_completed"
1777   "xor{l}\t%k0, %k0"
1778   [(set_attr "type" "alu1")
1779    (set_attr "mode" "SI")
1780    (set_attr "length_immediate" "0")])
1781
1782 (define_insn "*mov<mode>_or"
1783   [(set (match_operand:SWI48 0 "register_operand" "=r")
1784         (match_operand:SWI48 1 "const_int_operand" ""))
1785    (clobber (reg:CC FLAGS_REG))]
1786   "reload_completed
1787    && operands[1] == constm1_rtx"
1788   "or{<imodesuffix>}\t{%1, %0|%0, %1}"
1789   [(set_attr "type" "alu1")
1790    (set_attr "mode" "<MODE>")
1791    (set_attr "length_immediate" "1")])
1792
1793 (define_insn "*movoi_internal_avx"
1794   [(set (match_operand:OI 0 "nonimmediate_operand" "=x,x,m")
1795         (match_operand:OI 1 "vector_move_operand" "C,xm,x"))]
1796   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1797 {
1798   switch (which_alternative)
1799     {
1800     case 0:
1801       return standard_sse_constant_opcode (insn, operands[1]);
1802     case 1:
1803     case 2:
1804       if (misaligned_operand (operands[0], OImode)
1805           || misaligned_operand (operands[1], OImode))
1806         return "vmovdqu\t{%1, %0|%0, %1}";
1807       else
1808         return "vmovdqa\t{%1, %0|%0, %1}";
1809     default:
1810       gcc_unreachable ();
1811     }
1812 }
1813   [(set_attr "type" "sselog1,ssemov,ssemov")
1814    (set_attr "prefix" "vex")
1815    (set_attr "mode" "OI")])
1816
1817 (define_insn "*movti_internal_rex64"
1818   [(set (match_operand:TI 0 "nonimmediate_operand" "=!r,o,x,x,xm")
1819         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
1820   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1821 {
1822   switch (which_alternative)
1823     {
1824     case 0:
1825     case 1:
1826       return "#";
1827     case 2:
1828       return standard_sse_constant_opcode (insn, operands[1]);
1829     case 3:
1830     case 4:
1831       /* TDmode values are passed as TImode on the stack.  Moving them
1832          to stack may result in unaligned memory access.  */
1833       if (misaligned_operand (operands[0], TImode)
1834           || misaligned_operand (operands[1], TImode))
1835         {
1836           if (get_attr_mode (insn) == MODE_V4SF)
1837             return "%vmovups\t{%1, %0|%0, %1}";
1838           else
1839             return "%vmovdqu\t{%1, %0|%0, %1}";
1840         }
1841       else
1842         {
1843           if (get_attr_mode (insn) == MODE_V4SF)
1844             return "%vmovaps\t{%1, %0|%0, %1}";
1845           else
1846             return "%vmovdqa\t{%1, %0|%0, %1}";
1847         }
1848     default:
1849       gcc_unreachable ();
1850     }
1851 }
1852   [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
1853    (set_attr "prefix" "*,*,maybe_vex,maybe_vex,maybe_vex")
1854    (set (attr "mode")
1855         (cond [(eq_attr "alternative" "2,3")
1856                  (if_then_else
1857                    (match_test "optimize_function_for_size_p (cfun)")
1858                    (const_string "V4SF")
1859                    (const_string "TI"))
1860                (eq_attr "alternative" "4")
1861                  (if_then_else
1862                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
1863                         (match_test "optimize_function_for_size_p (cfun)"))
1864                    (const_string "V4SF")
1865                    (const_string "TI"))]
1866                (const_string "DI")))])
1867
1868 (define_split
1869   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1870         (match_operand:TI 1 "general_operand" ""))]
1871   "reload_completed
1872    && !SSE_REG_P (operands[0]) && !SSE_REG_P (operands[1])"
1873   [(const_int 0)]
1874   "ix86_split_long_move (operands); DONE;")
1875
1876 (define_insn "*movti_internal_sse"
1877   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
1878         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
1879   "TARGET_SSE && !TARGET_64BIT
1880    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1881 {
1882   switch (which_alternative)
1883     {
1884     case 0:
1885       return standard_sse_constant_opcode (insn, operands[1]);
1886     case 1:
1887     case 2:
1888       /* TDmode values are passed as TImode on the stack.  Moving them
1889          to stack may result in unaligned memory access.  */
1890       if (misaligned_operand (operands[0], TImode)
1891           || misaligned_operand (operands[1], TImode))
1892         {
1893           if (get_attr_mode (insn) == MODE_V4SF)
1894             return "%vmovups\t{%1, %0|%0, %1}";
1895           else
1896             return "%vmovdqu\t{%1, %0|%0, %1}";
1897         }
1898       else
1899         {
1900           if (get_attr_mode (insn) == MODE_V4SF)
1901             return "%vmovaps\t{%1, %0|%0, %1}";
1902           else
1903             return "%vmovdqa\t{%1, %0|%0, %1}";
1904         }
1905     default:
1906       gcc_unreachable ();
1907     }
1908 }
1909   [(set_attr "type" "sselog1,ssemov,ssemov")
1910    (set_attr "prefix" "maybe_vex")
1911    (set (attr "mode")
1912         (cond [(ior (not (match_test "TARGET_SSE2"))
1913                     (match_test "optimize_function_for_size_p (cfun)"))
1914                  (const_string "V4SF")
1915                (and (eq_attr "alternative" "2")
1916                     (match_test "TARGET_SSE_TYPELESS_STORES"))
1917                  (const_string "V4SF")]
1918               (const_string "TI")))])
1919
1920 (define_insn "*movdi_internal_rex64"
1921   [(set (match_operand:DI 0 "nonimmediate_operand"
1922           "=r,r  ,r,m ,!o,*y,m*y,?*y,?r ,?*Ym,*x,m ,*x,*x,?r ,?*Yi,?*x,?*Ym")
1923         (match_operand:DI 1 "general_operand"
1924           "Z ,rem,i,re,n ,C ,*y ,m  ,*Ym,r   ,C ,*x,*x,m ,*Yi,r   ,*Ym,*x"))]
1925   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1926 {
1927   switch (get_attr_type (insn))
1928     {
1929     case TYPE_SSECVT:
1930       if (SSE_REG_P (operands[0]))
1931         return "movq2dq\t{%1, %0|%0, %1}";
1932       else
1933         return "movdq2q\t{%1, %0|%0, %1}";
1934
1935     case TYPE_SSEMOV:
1936       if (get_attr_mode (insn) == MODE_TI)
1937         return "%vmovdqa\t{%1, %0|%0, %1}";
1938       /* Handle broken assemblers that require movd instead of movq.  */
1939       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1940         return "%vmovd\t{%1, %0|%0, %1}";
1941       else
1942         return "%vmovq\t{%1, %0|%0, %1}";
1943
1944     case TYPE_MMXMOV:
1945       /* Handle broken assemblers that require movd instead of movq.  */
1946       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1947         return "movd\t{%1, %0|%0, %1}";
1948       else
1949         return "movq\t{%1, %0|%0, %1}";
1950
1951     case TYPE_SSELOG1:
1952       return standard_sse_constant_opcode (insn, operands[1]);
1953
1954     case TYPE_MMX:
1955       return "pxor\t%0, %0";
1956
1957     case TYPE_MULTI:
1958       return "#";
1959
1960     case TYPE_LEA:
1961       return "lea{q}\t{%E1, %0|%0, %E1}";
1962
1963     default:
1964       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1965       if (get_attr_mode (insn) == MODE_SI)
1966         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1967       else if (which_alternative == 2)
1968         return "movabs{q}\t{%1, %0|%0, %1}";
1969       else if (ix86_use_lea_for_mov (insn, operands))
1970         return "lea{q}\t{%E1, %0|%0, %E1}";
1971       else
1972         return "mov{q}\t{%1, %0|%0, %1}";
1973     }
1974 }
1975   [(set (attr "type")
1976      (cond [(eq_attr "alternative" "4")
1977               (const_string "multi")
1978             (eq_attr "alternative" "5")
1979               (const_string "mmx")
1980             (eq_attr "alternative" "6,7,8,9")
1981               (const_string "mmxmov")
1982             (eq_attr "alternative" "10")
1983               (const_string "sselog1")
1984             (eq_attr "alternative" "11,12,13,14,15")
1985               (const_string "ssemov")
1986             (eq_attr "alternative" "16,17")
1987               (const_string "ssecvt")
1988             (match_operand 1 "pic_32bit_operand" "")
1989               (const_string "lea")
1990            ]
1991            (const_string "imov")))
1992    (set (attr "modrm")
1993      (if_then_else
1994        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
1995          (const_string "0")
1996          (const_string "*")))
1997    (set (attr "length_immediate")
1998      (if_then_else
1999        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
2000          (const_string "8")
2001          (const_string "*")))
2002    (set (attr "prefix_rex")
2003      (if_then_else (eq_attr "alternative" "8,9")
2004        (const_string "1")
2005        (const_string "*")))
2006    (set (attr "prefix_data16")
2007      (if_then_else (eq_attr "alternative" "11")
2008        (const_string "1")
2009        (const_string "*")))
2010    (set (attr "prefix")
2011      (if_then_else (eq_attr "alternative" "10,11,12,13,14,15")
2012        (const_string "maybe_vex")
2013        (const_string "orig")))
2014    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,TI,DI,TI,DI,DI,DI,DI,DI")])
2015
2016 ;; Reload patterns to support multi-word load/store
2017 ;; with non-offsetable address.
2018 (define_expand "reload_noff_store"
2019   [(parallel [(match_operand 0 "memory_operand" "=m")
2020               (match_operand 1 "register_operand" "r")
2021               (match_operand:DI 2 "register_operand" "=&r")])]
2022   "TARGET_64BIT"
2023 {
2024   rtx mem = operands[0];
2025   rtx addr = XEXP (mem, 0);
2026
2027   emit_move_insn (operands[2], addr);
2028   mem = replace_equiv_address_nv (mem, operands[2]);
2029
2030   emit_insn (gen_rtx_SET (VOIDmode, mem, operands[1]));
2031   DONE;
2032 })
2033
2034 (define_expand "reload_noff_load"
2035   [(parallel [(match_operand 0 "register_operand" "=r")
2036               (match_operand 1 "memory_operand" "m")
2037               (match_operand:DI 2 "register_operand" "=r")])]
2038   "TARGET_64BIT"
2039 {
2040   rtx mem = operands[1];
2041   rtx addr = XEXP (mem, 0);
2042
2043   emit_move_insn (operands[2], addr);
2044   mem = replace_equiv_address_nv (mem, operands[2]);
2045
2046   emit_insn (gen_rtx_SET (VOIDmode, operands[0], mem));
2047   DONE;
2048 })
2049
2050 ;; Convert impossible stores of immediate to existing instructions.
2051 ;; First try to get scratch register and go through it.  In case this
2052 ;; fails, move by 32bit parts.
2053 (define_peephole2
2054   [(match_scratch:DI 2 "r")
2055    (set (match_operand:DI 0 "memory_operand" "")
2056         (match_operand:DI 1 "immediate_operand" ""))]
2057   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2058    && !x86_64_immediate_operand (operands[1], DImode)"
2059   [(set (match_dup 2) (match_dup 1))
2060    (set (match_dup 0) (match_dup 2))])
2061
2062 ;; We need to define this as both peepholer and splitter for case
2063 ;; peephole2 pass is not run.
2064 ;; "&& 1" is needed to keep it from matching the previous pattern.
2065 (define_peephole2
2066   [(set (match_operand:DI 0 "memory_operand" "")
2067         (match_operand:DI 1 "immediate_operand" ""))]
2068   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2069    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2070   [(set (match_dup 2) (match_dup 3))
2071    (set (match_dup 4) (match_dup 5))]
2072   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2073
2074 (define_split
2075   [(set (match_operand:DI 0 "memory_operand" "")
2076         (match_operand:DI 1 "immediate_operand" ""))]
2077   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2078                     ? epilogue_completed : reload_completed)
2079    && !symbolic_operand (operands[1], DImode)
2080    && !x86_64_immediate_operand (operands[1], DImode)"
2081   [(set (match_dup 2) (match_dup 3))
2082    (set (match_dup 4) (match_dup 5))]
2083   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2084
2085 (define_insn "*movdi_internal"
2086   [(set (match_operand:DI 0 "nonimmediate_operand"
2087           "=r  ,o  ,*y,m*y,*y,*x,m ,*x,*x,*x,m ,*x,*x,?*x,?*Ym")
2088         (match_operand:DI 1 "general_operand"
2089           "riFo,riF,C ,*y ,m ,C ,*x,*x,m ,C ,*x,*x,m ,*Ym,*x"))]
2090   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2091 {
2092   switch (get_attr_type (insn))
2093     {
2094     case TYPE_SSECVT:
2095       if (SSE_REG_P (operands[0]))
2096         return "movq2dq\t{%1, %0|%0, %1}";
2097       else
2098         return "movdq2q\t{%1, %0|%0, %1}";
2099
2100     case TYPE_SSEMOV:
2101       switch (get_attr_mode (insn))
2102         {
2103         case MODE_TI:
2104           return "%vmovdqa\t{%1, %0|%0, %1}";
2105         case MODE_DI:
2106            return "%vmovq\t{%1, %0|%0, %1}";
2107         case MODE_V4SF:
2108           return "movaps\t{%1, %0|%0, %1}";
2109         case MODE_V2SF:
2110           return "movlps\t{%1, %0|%0, %1}";
2111         default:
2112           gcc_unreachable ();
2113         }
2114
2115     case TYPE_MMXMOV:
2116       return "movq\t{%1, %0|%0, %1}";
2117
2118     case TYPE_SSELOG1:
2119       return standard_sse_constant_opcode (insn, operands[1]);
2120
2121     case TYPE_MMX:
2122       return "pxor\t%0, %0";
2123
2124     case TYPE_MULTI:
2125       return "#";
2126
2127     default:
2128       gcc_unreachable ();
2129     }
2130 }
2131   [(set (attr "isa")
2132      (cond [(eq_attr "alternative" "5,6,7,8,13,14")
2133               (const_string "sse2")
2134             (eq_attr "alternative" "9,10,11,12")
2135               (const_string "noavx")
2136            ]
2137            (const_string "*")))
2138    (set (attr "type")
2139      (cond [(eq_attr "alternative" "0,1")
2140               (const_string "multi")
2141             (eq_attr "alternative" "2")
2142               (const_string "mmx")
2143             (eq_attr "alternative" "3,4")
2144               (const_string "mmxmov")
2145             (eq_attr "alternative" "5,9")
2146               (const_string "sselog1")
2147             (eq_attr "alternative" "13,14")
2148               (const_string "ssecvt")
2149            ]
2150            (const_string "ssemov")))
2151    (set (attr "prefix")
2152      (if_then_else (eq_attr "alternative" "5,6,7,8")
2153        (const_string "maybe_vex")
2154        (const_string "orig")))
2155    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF,DI,DI")])
2156
2157 (define_split
2158   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2159         (match_operand:DI 1 "general_operand" ""))]
2160   "!TARGET_64BIT && reload_completed
2161    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))
2162    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
2163   [(const_int 0)]
2164   "ix86_split_long_move (operands); DONE;")
2165
2166 (define_insn "*movsi_internal"
2167   [(set (match_operand:SI 0 "nonimmediate_operand"
2168                         "=r,m ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
2169         (match_operand:SI 1 "general_operand"
2170                         "g ,re,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r   ,m "))]
2171   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2172 {
2173   switch (get_attr_type (insn))
2174     {
2175     case TYPE_SSELOG1:
2176       return standard_sse_constant_opcode (insn, operands[1]);
2177
2178     case TYPE_SSEMOV:
2179       switch (get_attr_mode (insn))
2180         {
2181         case MODE_TI:
2182           return "%vmovdqa\t{%1, %0|%0, %1}";
2183         case MODE_V4SF:
2184           return "%vmovaps\t{%1, %0|%0, %1}";
2185         case MODE_SI:
2186           return "%vmovd\t{%1, %0|%0, %1}";
2187         case MODE_SF:
2188           return "%vmovss\t{%1, %0|%0, %1}";
2189         default:
2190           gcc_unreachable ();
2191         }
2192
2193     case TYPE_MMX:
2194       return "pxor\t%0, %0";
2195
2196     case TYPE_MMXMOV:
2197       if (get_attr_mode (insn) == MODE_DI)
2198         return "movq\t{%1, %0|%0, %1}";
2199       return "movd\t{%1, %0|%0, %1}";
2200
2201     case TYPE_LEA:
2202       return "lea{l}\t{%E1, %0|%0, %E1}";
2203
2204     default:
2205       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2206       if (ix86_use_lea_for_mov (insn, operands))
2207         return "lea{l}\t{%E1, %0|%0, %E1}";
2208       else
2209         return "mov{l}\t{%1, %0|%0, %1}";
2210     }
2211 }
2212   [(set (attr "type")
2213      (cond [(eq_attr "alternative" "2")
2214               (const_string "mmx")
2215             (eq_attr "alternative" "3,4,5")
2216               (const_string "mmxmov")
2217             (eq_attr "alternative" "6")
2218               (const_string "sselog1")
2219             (eq_attr "alternative" "7,8,9,10,11")
2220               (const_string "ssemov")
2221             (match_operand 1 "pic_32bit_operand" "")
2222               (const_string "lea")
2223            ]
2224            (const_string "imov")))
2225    (set (attr "prefix")
2226      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5")
2227        (const_string "orig")
2228        (const_string "maybe_vex")))
2229    (set (attr "prefix_data16")
2230      (if_then_else (and (eq_attr "type" "ssemov") (eq_attr "mode" "SI"))
2231        (const_string "1")
2232        (const_string "*")))
2233    (set (attr "mode")
2234      (cond [(eq_attr "alternative" "2,3")
2235               (const_string "DI")
2236             (eq_attr "alternative" "6,7")
2237               (if_then_else
2238                 (not (match_test "TARGET_SSE2"))
2239                 (const_string "V4SF")
2240                 (const_string "TI"))
2241             (and (eq_attr "alternative" "8,9,10,11")
2242                  (not (match_test "TARGET_SSE2")))
2243               (const_string "SF")
2244            ]
2245            (const_string "SI")))])
2246
2247 (define_insn "*movhi_internal"
2248   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
2249         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
2250   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2251 {
2252   switch (get_attr_type (insn))
2253     {
2254     case TYPE_IMOVX:
2255       /* movzwl is faster than movw on p2 due to partial word stalls,
2256          though not as fast as an aligned movl.  */
2257       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
2258     default:
2259       if (get_attr_mode (insn) == MODE_SI)
2260         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2261       else
2262         return "mov{w}\t{%1, %0|%0, %1}";
2263     }
2264 }
2265   [(set (attr "type")
2266      (cond [(match_test "optimize_function_for_size_p (cfun)")
2267               (const_string "imov")
2268             (and (eq_attr "alternative" "0")
2269                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2270                       (not (match_test "TARGET_HIMODE_MATH"))))
2271               (const_string "imov")
2272             (and (eq_attr "alternative" "1,2")
2273                  (match_operand:HI 1 "aligned_operand" ""))
2274               (const_string "imov")
2275             (and (match_test "TARGET_MOVX")
2276                  (eq_attr "alternative" "0,2"))
2277               (const_string "imovx")
2278            ]
2279            (const_string "imov")))
2280     (set (attr "mode")
2281       (cond [(eq_attr "type" "imovx")
2282                (const_string "SI")
2283              (and (eq_attr "alternative" "1,2")
2284                   (match_operand:HI 1 "aligned_operand" ""))
2285                (const_string "SI")
2286              (and (eq_attr "alternative" "0")
2287                   (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2288                        (not (match_test "TARGET_HIMODE_MATH"))))
2289                (const_string "SI")
2290             ]
2291             (const_string "HI")))])
2292
2293 ;; Situation is quite tricky about when to choose full sized (SImode) move
2294 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
2295 ;; partial register dependency machines (such as AMD Athlon), where QImode
2296 ;; moves issue extra dependency and for partial register stalls machines
2297 ;; that don't use QImode patterns (and QImode move cause stall on the next
2298 ;; instruction).
2299 ;;
2300 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
2301 ;; register stall machines with, where we use QImode instructions, since
2302 ;; partial register stall can be caused there.  Then we use movzx.
2303 (define_insn "*movqi_internal"
2304   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
2305         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
2306   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2307 {
2308   switch (get_attr_type (insn))
2309     {
2310     case TYPE_IMOVX:
2311       gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
2312       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
2313     default:
2314       if (get_attr_mode (insn) == MODE_SI)
2315         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2316       else
2317         return "mov{b}\t{%1, %0|%0, %1}";
2318     }
2319 }
2320   [(set (attr "type")
2321      (cond [(and (eq_attr "alternative" "5")
2322                  (not (match_operand:QI 1 "aligned_operand" "")))
2323               (const_string "imovx")
2324             (match_test "optimize_function_for_size_p (cfun)")
2325               (const_string "imov")
2326             (and (eq_attr "alternative" "3")
2327                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2328                       (not (match_test "TARGET_QIMODE_MATH"))))
2329               (const_string "imov")
2330             (eq_attr "alternative" "3,5")
2331               (const_string "imovx")
2332             (and (match_test "TARGET_MOVX")
2333                  (eq_attr "alternative" "2"))
2334               (const_string "imovx")
2335            ]
2336            (const_string "imov")))
2337    (set (attr "mode")
2338       (cond [(eq_attr "alternative" "3,4,5")
2339                (const_string "SI")
2340              (eq_attr "alternative" "6")
2341                (const_string "QI")
2342              (eq_attr "type" "imovx")
2343                (const_string "SI")
2344              (and (eq_attr "type" "imov")
2345                   (and (eq_attr "alternative" "0,1")
2346                        (and (match_test "TARGET_PARTIAL_REG_DEPENDENCY")
2347                             (and (not (match_test "optimize_function_for_size_p (cfun)"))
2348                                  (not (match_test "TARGET_PARTIAL_REG_STALL"))))))
2349                (const_string "SI")
2350              ;; Avoid partial register stalls when not using QImode arithmetic
2351              (and (eq_attr "type" "imov")
2352                   (and (eq_attr "alternative" "0,1")
2353                        (and (match_test "TARGET_PARTIAL_REG_STALL")
2354                             (not (match_test "TARGET_QIMODE_MATH")))))
2355                (const_string "SI")
2356            ]
2357            (const_string "QI")))])
2358
2359 ;; Stores and loads of ax to arbitrary constant address.
2360 ;; We fake an second form of instruction to force reload to load address
2361 ;; into register when rax is not available
2362 (define_insn "*movabs<mode>_1"
2363   [(set (mem:SWI1248x (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2364         (match_operand:SWI1248x 1 "nonmemory_operand" "a,r<i>"))]
2365   "TARGET_LP64 && ix86_check_movabs (insn, 0)"
2366   "@
2367    movabs{<imodesuffix>}\t{%1, %P0|%P0, %1}
2368    mov{<imodesuffix>}\t{%1, %a0|%a0, %1}"
2369   [(set_attr "type" "imov")
2370    (set_attr "modrm" "0,*")
2371    (set_attr "length_address" "8,0")
2372    (set_attr "length_immediate" "0,*")
2373    (set_attr "memory" "store")
2374    (set_attr "mode" "<MODE>")])
2375
2376 (define_insn "*movabs<mode>_2"
2377   [(set (match_operand:SWI1248x 0 "register_operand" "=a,r")
2378         (mem:SWI1248x (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2379   "TARGET_LP64 && ix86_check_movabs (insn, 1)"
2380   "@
2381    movabs{<imodesuffix>}\t{%P1, %0|%0, %P1}
2382    mov{<imodesuffix>}\t{%a1, %0|%0, %a1}"
2383   [(set_attr "type" "imov")
2384    (set_attr "modrm" "0,*")
2385    (set_attr "length_address" "8,0")
2386    (set_attr "length_immediate" "0")
2387    (set_attr "memory" "load")
2388    (set_attr "mode" "<MODE>")])
2389
2390 (define_insn "*swap<mode>"
2391   [(set (match_operand:SWI48 0 "register_operand" "+r")
2392         (match_operand:SWI48 1 "register_operand" "+r"))
2393    (set (match_dup 1)
2394         (match_dup 0))]
2395   ""
2396   "xchg{<imodesuffix>}\t%1, %0"
2397   [(set_attr "type" "imov")
2398    (set_attr "mode" "<MODE>")
2399    (set_attr "pent_pair" "np")
2400    (set_attr "athlon_decode" "vector")
2401    (set_attr "amdfam10_decode" "double")
2402    (set_attr "bdver1_decode" "double")])
2403
2404 (define_insn "*swap<mode>_1"
2405   [(set (match_operand:SWI12 0 "register_operand" "+r")
2406         (match_operand:SWI12 1 "register_operand" "+r"))
2407    (set (match_dup 1)
2408         (match_dup 0))]
2409   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
2410   "xchg{l}\t%k1, %k0"
2411   [(set_attr "type" "imov")
2412    (set_attr "mode" "SI")
2413    (set_attr "pent_pair" "np")
2414    (set_attr "athlon_decode" "vector")
2415    (set_attr "amdfam10_decode" "double")
2416    (set_attr "bdver1_decode" "double")])
2417
2418 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL
2419 ;; is disabled for AMDFAM10
2420 (define_insn "*swap<mode>_2"
2421   [(set (match_operand:SWI12 0 "register_operand" "+<r>")
2422         (match_operand:SWI12 1 "register_operand" "+<r>"))
2423    (set (match_dup 1)
2424         (match_dup 0))]
2425   "TARGET_PARTIAL_REG_STALL"
2426   "xchg{<imodesuffix>}\t%1, %0"
2427   [(set_attr "type" "imov")
2428    (set_attr "mode" "<MODE>")
2429    (set_attr "pent_pair" "np")
2430    (set_attr "athlon_decode" "vector")])
2431
2432 (define_expand "movstrict<mode>"
2433   [(set (strict_low_part (match_operand:SWI12 0 "nonimmediate_operand" ""))
2434         (match_operand:SWI12 1 "general_operand" ""))]
2435   ""
2436 {
2437   if (TARGET_PARTIAL_REG_STALL && optimize_function_for_speed_p (cfun))
2438     FAIL;
2439   if (GET_CODE (operands[0]) == SUBREG
2440       && GET_MODE_CLASS (GET_MODE (SUBREG_REG (operands[0]))) != MODE_INT)
2441     FAIL;
2442   /* Don't generate memory->memory moves, go through a register */
2443   if (MEM_P (operands[0]) && MEM_P (operands[1]))
2444     operands[1] = force_reg (<MODE>mode, operands[1]);
2445 })
2446
2447 (define_insn "*movstrict<mode>_1"
2448   [(set (strict_low_part
2449           (match_operand:SWI12 0 "nonimmediate_operand" "+<r>m,<r>"))
2450         (match_operand:SWI12 1 "general_operand" "<r>n,m"))]
2451   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
2452    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2453   "mov{<imodesuffix>}\t{%1, %0|%0, %1}"
2454   [(set_attr "type" "imov")
2455    (set_attr "mode" "<MODE>")])
2456
2457 (define_insn "*movstrict<mode>_xor"
2458   [(set (strict_low_part (match_operand:SWI12 0 "register_operand" "+<r>"))
2459         (match_operand:SWI12 1 "const0_operand" ""))
2460    (clobber (reg:CC FLAGS_REG))]
2461   "reload_completed"
2462   "xor{<imodesuffix>}\t%0, %0"
2463   [(set_attr "type" "alu1")
2464    (set_attr "mode" "<MODE>")
2465    (set_attr "length_immediate" "0")])
2466
2467 (define_insn "*mov<mode>_extv_1"
2468   [(set (match_operand:SWI24 0 "register_operand" "=R")
2469         (sign_extract:SWI24 (match_operand 1 "ext_register_operand" "Q")
2470                             (const_int 8)
2471                             (const_int 8)))]
2472   ""
2473   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
2474   [(set_attr "type" "imovx")
2475    (set_attr "mode" "SI")])
2476
2477 (define_insn "*movqi_extv_1_rex64"
2478   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2479         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2480                          (const_int 8)
2481                          (const_int 8)))]
2482   "TARGET_64BIT"
2483 {
2484   switch (get_attr_type (insn))
2485     {
2486     case TYPE_IMOVX:
2487       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2488     default:
2489       return "mov{b}\t{%h1, %0|%0, %h1}";
2490     }
2491 }
2492   [(set (attr "type")
2493      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2494                         (match_test "TARGET_MOVX"))
2495         (const_string "imovx")
2496         (const_string "imov")))
2497    (set (attr "mode")
2498      (if_then_else (eq_attr "type" "imovx")
2499         (const_string "SI")
2500         (const_string "QI")))])
2501
2502 (define_insn "*movqi_extv_1"
2503   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
2504         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2505                          (const_int 8)
2506                          (const_int 8)))]
2507   "!TARGET_64BIT"
2508 {
2509   switch (get_attr_type (insn))
2510     {
2511     case TYPE_IMOVX:
2512       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2513     default:
2514       return "mov{b}\t{%h1, %0|%0, %h1}";
2515     }
2516 }
2517   [(set (attr "type")
2518      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2519                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2520                              (match_test "TARGET_MOVX")))
2521         (const_string "imovx")
2522         (const_string "imov")))
2523    (set (attr "mode")
2524      (if_then_else (eq_attr "type" "imovx")
2525         (const_string "SI")
2526         (const_string "QI")))])
2527
2528 (define_insn "*mov<mode>_extzv_1"
2529   [(set (match_operand:SWI48 0 "register_operand" "=R")
2530         (zero_extract:SWI48 (match_operand 1 "ext_register_operand" "Q")
2531                             (const_int 8)
2532                             (const_int 8)))]
2533   ""
2534   "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
2535   [(set_attr "type" "imovx")
2536    (set_attr "mode" "SI")])
2537
2538 (define_insn "*movqi_extzv_2_rex64"
2539   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2540         (subreg:QI
2541           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2542                            (const_int 8)
2543                            (const_int 8)) 0))]
2544   "TARGET_64BIT"
2545 {
2546   switch (get_attr_type (insn))
2547     {
2548     case TYPE_IMOVX:
2549       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2550     default:
2551       return "mov{b}\t{%h1, %0|%0, %h1}";
2552     }
2553 }
2554   [(set (attr "type")
2555      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2556                         (match_test "TARGET_MOVX"))
2557         (const_string "imovx")
2558         (const_string "imov")))
2559    (set (attr "mode")
2560      (if_then_else (eq_attr "type" "imovx")
2561         (const_string "SI")
2562         (const_string "QI")))])
2563
2564 (define_insn "*movqi_extzv_2"
2565   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2566         (subreg:QI
2567           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2568                            (const_int 8)
2569                            (const_int 8)) 0))]
2570   "!TARGET_64BIT"
2571 {
2572   switch (get_attr_type (insn))
2573     {
2574     case TYPE_IMOVX:
2575       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2576     default:
2577       return "mov{b}\t{%h1, %0|%0, %h1}";
2578     }
2579 }
2580   [(set (attr "type")
2581      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2582                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2583                              (match_test "TARGET_MOVX")))
2584         (const_string "imovx")
2585         (const_string "imov")))
2586    (set (attr "mode")
2587      (if_then_else (eq_attr "type" "imovx")
2588         (const_string "SI")
2589         (const_string "QI")))])
2590
2591 (define_expand "mov<mode>_insv_1"
2592   [(set (zero_extract:SWI48 (match_operand 0 "ext_register_operand" "")
2593                             (const_int 8)
2594                             (const_int 8))
2595         (match_operand:SWI48 1 "nonmemory_operand" ""))])
2596
2597 (define_insn "*mov<mode>_insv_1_rex64"
2598   [(set (zero_extract:SWI48x (match_operand 0 "ext_register_operand" "+Q")
2599                              (const_int 8)
2600                              (const_int 8))
2601         (match_operand:SWI48x 1 "nonmemory_operand" "Qn"))]
2602   "TARGET_64BIT"
2603   "mov{b}\t{%b1, %h0|%h0, %b1}"
2604   [(set_attr "type" "imov")
2605    (set_attr "mode" "QI")])
2606
2607 (define_insn "*movsi_insv_1"
2608   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2609                          (const_int 8)
2610                          (const_int 8))
2611         (match_operand:SI 1 "general_operand" "Qmn"))]
2612   "!TARGET_64BIT"
2613   "mov{b}\t{%b1, %h0|%h0, %b1}"
2614   [(set_attr "type" "imov")
2615    (set_attr "mode" "QI")])
2616
2617 (define_insn "*movqi_insv_2"
2618   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2619                          (const_int 8)
2620                          (const_int 8))
2621         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2622                      (const_int 8)))]
2623   ""
2624   "mov{b}\t{%h1, %h0|%h0, %h1}"
2625   [(set_attr "type" "imov")
2626    (set_attr "mode" "QI")])
2627 \f
2628 ;; Floating point push instructions.
2629
2630 (define_insn "*pushtf"
2631   [(set (match_operand:TF 0 "push_operand" "=<,<,<")
2632         (match_operand:TF 1 "general_no_elim_operand" "x,Fo,*r"))]
2633   "TARGET_SSE2"
2634 {
2635   /* This insn should be already split before reg-stack.  */
2636   gcc_unreachable ();
2637 }
2638   [(set_attr "type" "multi")
2639    (set_attr "unit" "sse,*,*")
2640    (set_attr "mode" "TF,SI,SI")])
2641
2642 ;; %%% Kill this when call knows how to work this out.
2643 (define_split
2644   [(set (match_operand:TF 0 "push_operand" "")
2645         (match_operand:TF 1 "sse_reg_operand" ""))]
2646   "TARGET_SSE2 && reload_completed"
2647   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -16)))
2648    (set (mem:TF (reg:P SP_REG)) (match_dup 1))])
2649
2650 (define_insn "*pushxf"
2651   [(set (match_operand:XF 0 "push_operand" "=<,<")
2652         (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
2653   "optimize_function_for_speed_p (cfun)"
2654 {
2655   /* This insn should be already split before reg-stack.  */
2656   gcc_unreachable ();
2657 }
2658   [(set_attr "type" "multi")
2659    (set_attr "unit" "i387,*")
2660    (set_attr "mode" "XF,SI")])
2661
2662 ;; Size of pushxf is 3 (for sub) + 2 (for fstp) + memory operand size.
2663 ;; Size of pushxf using integer instructions is 3+3*memory operand size
2664 ;; Pushing using integer instructions is longer except for constants
2665 ;; and direct memory references (assuming that any given constant is pushed
2666 ;; only once, but this ought to be handled elsewhere).
2667
2668 (define_insn "*pushxf_nointeger"
2669   [(set (match_operand:XF 0 "push_operand" "=<,<")
2670         (match_operand:XF 1 "general_no_elim_operand" "f,*rFo"))]
2671   "optimize_function_for_size_p (cfun)"
2672 {
2673   /* This insn should be already split before reg-stack.  */
2674   gcc_unreachable ();
2675 }
2676   [(set_attr "type" "multi")
2677    (set_attr "unit" "i387,*")
2678    (set_attr "mode" "XF,SI")])
2679
2680 ;; %%% Kill this when call knows how to work this out.
2681 (define_split
2682   [(set (match_operand:XF 0 "push_operand" "")
2683         (match_operand:XF 1 "fp_register_operand" ""))]
2684   "reload_completed"
2685   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2686    (set (mem:XF (reg:P SP_REG)) (match_dup 1))]
2687   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
2688
2689 (define_insn "*pushdf_rex64"
2690   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2691         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFm,x"))]
2692   "TARGET_64BIT"
2693 {
2694   /* This insn should be already split before reg-stack.  */
2695   gcc_unreachable ();
2696 }
2697   [(set_attr "type" "multi")
2698    (set_attr "unit" "i387,*,*")
2699    (set_attr "mode" "DF,DI,DF")])
2700
2701 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2702 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2703 ;; On the average, pushdf using integers can be still shorter.
2704
2705 (define_insn "*pushdf"
2706   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2707         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFo,x"))]
2708   "!TARGET_64BIT"
2709 {
2710   /* This insn should be already split before reg-stack.  */
2711   gcc_unreachable ();
2712 }
2713   [(set_attr "isa" "*,*,sse2")
2714    (set_attr "type" "multi")
2715    (set_attr "unit" "i387,*,*")
2716    (set_attr "mode" "DF,DI,DF")])
2717
2718 ;; %%% Kill this when call knows how to work this out.
2719 (define_split
2720   [(set (match_operand:DF 0 "push_operand" "")
2721         (match_operand:DF 1 "any_fp_register_operand" ""))]
2722   "reload_completed"
2723   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
2724    (set (mem:DF (reg:P SP_REG)) (match_dup 1))])
2725
2726 (define_insn "*pushsf_rex64"
2727   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2728         (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2729   "TARGET_64BIT"
2730 {
2731   /* Anything else should be already split before reg-stack.  */
2732   gcc_assert (which_alternative == 1);
2733   return "push{q}\t%q1";
2734 }
2735   [(set_attr "type" "multi,push,multi")
2736    (set_attr "unit" "i387,*,*")
2737    (set_attr "mode" "SF,DI,SF")])
2738
2739 (define_insn "*pushsf"
2740   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2741         (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2742   "!TARGET_64BIT"
2743 {
2744   /* Anything else should be already split before reg-stack.  */
2745   gcc_assert (which_alternative == 1);
2746   return "push{l}\t%1";
2747 }
2748   [(set_attr "type" "multi,push,multi")
2749    (set_attr "unit" "i387,*,*")
2750    (set_attr "mode" "SF,SI,SF")])
2751
2752 ;; %%% Kill this when call knows how to work this out.
2753 (define_split
2754   [(set (match_operand:SF 0 "push_operand" "")
2755         (match_operand:SF 1 "any_fp_register_operand" ""))]
2756   "reload_completed"
2757   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2758    (set (mem:SF (reg:P SP_REG)) (match_dup 1))]
2759   "operands[2] = GEN_INT (-GET_MODE_SIZE (<P:MODE>mode));")
2760
2761 (define_split
2762   [(set (match_operand:SF 0 "push_operand" "")
2763         (match_operand:SF 1 "memory_operand" ""))]
2764   "reload_completed
2765    && (operands[2] = find_constant_src (insn))"
2766   [(set (match_dup 0) (match_dup 2))])
2767
2768 (define_split
2769   [(set (match_operand 0 "push_operand" "")
2770         (match_operand 1 "general_operand" ""))]
2771   "reload_completed
2772    && (GET_MODE (operands[0]) == TFmode
2773        || GET_MODE (operands[0]) == XFmode
2774        || GET_MODE (operands[0]) == DFmode)
2775    && !ANY_FP_REG_P (operands[1])"
2776   [(const_int 0)]
2777   "ix86_split_long_move (operands); DONE;")
2778 \f
2779 ;; Floating point move instructions.
2780
2781 (define_expand "movtf"
2782   [(set (match_operand:TF 0 "nonimmediate_operand" "")
2783         (match_operand:TF 1 "nonimmediate_operand" ""))]
2784   "TARGET_SSE2"
2785 {
2786   ix86_expand_move (TFmode, operands);
2787   DONE;
2788 })
2789
2790 (define_expand "mov<mode>"
2791   [(set (match_operand:X87MODEF 0 "nonimmediate_operand" "")
2792         (match_operand:X87MODEF 1 "general_operand" ""))]
2793   ""
2794   "ix86_expand_move (<MODE>mode, operands); DONE;")
2795
2796 (define_insn "*movtf_internal"
2797   [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?*r ,!o")
2798         (match_operand:TF 1 "general_operand"      "xm,x,C,*roF,F*r"))]
2799   "TARGET_SSE2
2800    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2801    && (!can_create_pseudo_p ()
2802        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2803        || GET_CODE (operands[1]) != CONST_DOUBLE
2804        || (optimize_function_for_size_p (cfun)
2805            && standard_sse_constant_p (operands[1])
2806            && !memory_operand (operands[0], TFmode))
2807        || (!TARGET_MEMORY_MISMATCH_STALL
2808            && memory_operand (operands[0], TFmode)))"
2809 {
2810   switch (which_alternative)
2811     {
2812     case 0:
2813     case 1:
2814       /* Handle misaligned load/store since we
2815          don't have movmisaligntf pattern. */
2816       if (misaligned_operand (operands[0], TFmode)
2817           || misaligned_operand (operands[1], TFmode))
2818         {
2819           if (get_attr_mode (insn) == MODE_V4SF)
2820             return "%vmovups\t{%1, %0|%0, %1}";
2821           else
2822             return "%vmovdqu\t{%1, %0|%0, %1}";
2823         }
2824       else
2825         {
2826           if (get_attr_mode (insn) == MODE_V4SF)
2827             return "%vmovaps\t{%1, %0|%0, %1}";
2828           else
2829             return "%vmovdqa\t{%1, %0|%0, %1}";
2830         }
2831
2832     case 2:
2833       return standard_sse_constant_opcode (insn, operands[1]);
2834
2835     case 3:
2836     case 4:
2837         return "#";
2838
2839     default:
2840       gcc_unreachable ();
2841     }
2842 }
2843   [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
2844    (set_attr "prefix" "maybe_vex,maybe_vex,maybe_vex,*,*")
2845    (set (attr "mode")
2846         (cond [(eq_attr "alternative" "0,2")
2847                  (if_then_else
2848                    (match_test "optimize_function_for_size_p (cfun)")
2849                    (const_string "V4SF")
2850                    (const_string "TI"))
2851                (eq_attr "alternative" "1")
2852                  (if_then_else
2853                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
2854                         (match_test "optimize_function_for_size_p (cfun)"))
2855                    (const_string "V4SF")
2856                    (const_string "TI"))]
2857                (const_string "DI")))])
2858
2859 ;; Possible store forwarding (partial memory) stall in alternative 4.
2860 (define_insn "*movxf_internal"
2861   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,?Yx*r ,!o")
2862         (match_operand:XF 1 "general_operand"      "fm,f,G,Yx*roF,FYx*r"))]
2863   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2864    && (!can_create_pseudo_p ()
2865        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2866        || GET_CODE (operands[1]) != CONST_DOUBLE
2867        || (optimize_function_for_size_p (cfun)
2868            && standard_80387_constant_p (operands[1]) > 0
2869            && !memory_operand (operands[0], XFmode))
2870        || (!TARGET_MEMORY_MISMATCH_STALL
2871            && memory_operand (operands[0], XFmode)))"
2872 {
2873   switch (which_alternative)
2874     {
2875     case 0:
2876     case 1:
2877       return output_387_reg_move (insn, operands);
2878
2879     case 2:
2880       return standard_80387_constant_opcode (operands[1]);
2881
2882     case 3:
2883     case 4:
2884       return "#";
2885
2886     default:
2887       gcc_unreachable ();
2888     }
2889 }
2890   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2891    (set_attr "mode" "XF,XF,XF,SI,SI")])
2892
2893 (define_insn "*movdf_internal_rex64"
2894   [(set (match_operand:DF 0 "nonimmediate_operand"
2895                 "=f,m,f,?r,?m,?r,!o,x,x,x,m,Yi,r ")
2896         (match_operand:DF 1 "general_operand"
2897                 "fm,f,G,rm,r ,F ,F ,C,x,m,x,r ,Yi"))]
2898   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2899    && (!can_create_pseudo_p ()
2900        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2901        || GET_CODE (operands[1]) != CONST_DOUBLE
2902        || (optimize_function_for_size_p (cfun)
2903            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
2904                 && standard_80387_constant_p (operands[1]) > 0)
2905                || (TARGET_SSE2 && TARGET_SSE_MATH
2906                    && standard_sse_constant_p (operands[1]))))
2907        || memory_operand (operands[0], DFmode))"
2908 {
2909   switch (which_alternative)
2910     {
2911     case 0:
2912     case 1:
2913       return output_387_reg_move (insn, operands);
2914
2915     case 2:
2916       return standard_80387_constant_opcode (operands[1]);
2917
2918     case 3:
2919     case 4:
2920       return "mov{q}\t{%1, %0|%0, %1}";
2921
2922     case 5:
2923       return "movabs{q}\t{%1, %0|%0, %1}";
2924
2925     case 6:
2926       return "#";
2927
2928     case 7:
2929       return standard_sse_constant_opcode (insn, operands[1]);
2930
2931     case 8:
2932     case 9:
2933     case 10:
2934       switch (get_attr_mode (insn))
2935         {
2936         case MODE_V2DF:
2937           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
2938             return "%vmovapd\t{%1, %0|%0, %1}";
2939         case MODE_V4SF:
2940           return "%vmovaps\t{%1, %0|%0, %1}";
2941
2942         case MODE_DI:
2943           return "%vmovq\t{%1, %0|%0, %1}";
2944         case MODE_DF:
2945           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
2946             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
2947           return "%vmovsd\t{%1, %0|%0, %1}";
2948         case MODE_V1DF:
2949           return "%vmovlpd\t{%1, %d0|%d0, %1}";
2950         case MODE_V2SF:
2951           return "%vmovlps\t{%1, %d0|%d0, %1}";
2952         default:
2953           gcc_unreachable ();
2954         }
2955
2956     case 11:
2957     case 12:
2958       /* Handle broken assemblers that require movd instead of movq.  */
2959       return "%vmovd\t{%1, %0|%0, %1}";
2960
2961     default:
2962       gcc_unreachable();
2963     }
2964 }
2965   [(set (attr "type")
2966         (cond [(eq_attr "alternative" "0,1,2")
2967                  (const_string "fmov")
2968                (eq_attr "alternative" "3,4,5")
2969                  (const_string "imov")
2970                (eq_attr "alternative" "6")
2971                  (const_string "multi")
2972                (eq_attr "alternative" "7")
2973                  (const_string "sselog1")
2974               ]
2975               (const_string "ssemov")))
2976    (set (attr "modrm")
2977      (if_then_else
2978        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
2979          (const_string "0")
2980          (const_string "*")))
2981    (set (attr "length_immediate")
2982      (if_then_else
2983        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
2984          (const_string "8")
2985          (const_string "*")))
2986    (set (attr "prefix")
2987      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5,6")
2988        (const_string "orig")
2989        (const_string "maybe_vex")))
2990    (set (attr "prefix_data16")
2991      (if_then_else (eq_attr "mode" "V1DF")
2992        (const_string "1")
2993        (const_string "*")))
2994    (set (attr "mode")
2995         (cond [(eq_attr "alternative" "0,1,2")
2996                  (const_string "DF")
2997                (eq_attr "alternative" "3,4,5,6,11,12")
2998                  (const_string "DI")
2999
3000                /* xorps is one byte shorter.  */
3001                (eq_attr "alternative" "7")
3002                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3003                           (const_string "V4SF")
3004                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3005                           (const_string "TI")
3006                        ]
3007                        (const_string "V2DF"))
3008
3009                /* For architectures resolving dependencies on
3010                   whole SSE registers use APD move to break dependency
3011                   chains, otherwise use short move to avoid extra work.
3012
3013                   movaps encodes one byte shorter.  */
3014                (eq_attr "alternative" "8")
3015                  (cond
3016                    [(match_test "optimize_function_for_size_p (cfun)")
3017                       (const_string "V4SF")
3018                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3019                       (const_string "V2DF")
3020                    ]
3021                    (const_string "DF"))
3022                /* For architectures resolving dependencies on register
3023                   parts we may avoid extra work to zero out upper part
3024                   of register.  */
3025                (eq_attr "alternative" "9")
3026                  (if_then_else
3027                    (match_test "TARGET_SSE_SPLIT_REGS")
3028                    (const_string "V1DF")
3029                    (const_string "DF"))
3030               ]
3031               (const_string "DF")))])
3032
3033 ;; Possible store forwarding (partial memory) stall in alternative 4.
3034 (define_insn "*movdf_internal"
3035   [(set (match_operand:DF 0 "nonimmediate_operand"
3036                 "=f,m,f,?Yd*r ,!o   ,x,x,x,m,*x,*x,*x,m")
3037         (match_operand:DF 1 "general_operand"
3038                 "fm,f,G,Yd*roF,FYd*r,C,x,m,x,C ,*x,m ,*x"))]
3039   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3040    && (!can_create_pseudo_p ()
3041        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3042        || GET_CODE (operands[1]) != CONST_DOUBLE
3043        || (optimize_function_for_size_p (cfun)
3044            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
3045                 && standard_80387_constant_p (operands[1]) > 0)
3046                || (TARGET_SSE2 && TARGET_SSE_MATH
3047                    && standard_sse_constant_p (operands[1])))
3048            && !memory_operand (operands[0], DFmode))
3049        || (!TARGET_MEMORY_MISMATCH_STALL
3050            && memory_operand (operands[0], DFmode)))"
3051 {
3052   switch (which_alternative)
3053     {
3054     case 0:
3055     case 1:
3056       return output_387_reg_move (insn, operands);
3057
3058     case 2:
3059       return standard_80387_constant_opcode (operands[1]);
3060
3061     case 3:
3062     case 4:
3063       return "#";
3064
3065     case 5:
3066     case 9:
3067       return standard_sse_constant_opcode (insn, operands[1]);
3068
3069     case 6:
3070     case 7:
3071     case 8:
3072     case 10:
3073     case 11:
3074     case 12:
3075       switch (get_attr_mode (insn))
3076         {
3077         case MODE_V2DF:
3078           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
3079             return "%vmovapd\t{%1, %0|%0, %1}";
3080         case MODE_V4SF:
3081           return "%vmovaps\t{%1, %0|%0, %1}";
3082
3083         case MODE_DI:
3084           return "%vmovq\t{%1, %0|%0, %1}";
3085         case MODE_DF:
3086           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
3087             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3088           return "%vmovsd\t{%1, %0|%0, %1}";
3089         case MODE_V1DF:
3090           return "%vmovlpd\t{%1, %d0|%d0, %1}";
3091         case MODE_V2SF:
3092           return "%vmovlps\t{%1, %d0|%d0, %1}";
3093         default:
3094           gcc_unreachable ();
3095         }
3096
3097     default:
3098       gcc_unreachable ();
3099     }
3100 }
3101   [(set (attr "isa")
3102      (if_then_else (eq_attr "alternative" "5,6,7,8")
3103        (const_string "sse2")
3104        (const_string "*")))
3105    (set (attr "type")
3106         (cond [(eq_attr "alternative" "0,1,2")
3107                  (const_string "fmov")
3108                (eq_attr "alternative" "3,4")
3109                  (const_string "multi")
3110                (eq_attr "alternative" "5,9")
3111                  (const_string "sselog1")
3112               ]
3113               (const_string "ssemov")))
3114    (set (attr "prefix")
3115      (if_then_else (eq_attr "alternative" "0,1,2,3,4")
3116        (const_string "orig")
3117        (const_string "maybe_vex")))
3118    (set (attr "prefix_data16")
3119      (if_then_else (eq_attr "mode" "V1DF")
3120        (const_string "1")
3121        (const_string "*")))
3122    (set (attr "mode")
3123         (cond [(eq_attr "alternative" "0,1,2")
3124                  (const_string "DF")
3125                (eq_attr "alternative" "3,4")
3126                  (const_string "SI")
3127
3128                /* For SSE1, we have many fewer alternatives.  */
3129                (not (match_test "TARGET_SSE2"))
3130                  (if_then_else
3131                    (eq_attr "alternative" "5,6,9,10")
3132                    (const_string "V4SF")
3133                    (const_string "V2SF"))
3134
3135                /* xorps is one byte shorter.  */
3136                (eq_attr "alternative" "5,9")
3137                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3138                           (const_string "V4SF")
3139                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3140                           (const_string "TI")
3141                        ]
3142                        (const_string "V2DF"))
3143
3144                /* For architectures resolving dependencies on
3145                   whole SSE registers use APD move to break dependency
3146                   chains, otherwise use short move to avoid extra work.
3147
3148                   movaps encodes one byte shorter.  */
3149                (eq_attr "alternative" "6,10")
3150                  (cond
3151                    [(match_test "optimize_function_for_size_p (cfun)")
3152                       (const_string "V4SF")
3153                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3154                       (const_string "V2DF")
3155                    ]
3156                    (const_string "DF"))
3157                /* For architectures resolving dependencies on register
3158                   parts we may avoid extra work to zero out upper part
3159                   of register.  */
3160                (eq_attr "alternative" "7,11")
3161                  (if_then_else
3162                    (match_test "TARGET_SSE_SPLIT_REGS")
3163                    (const_string "V1DF")
3164                    (const_string "DF"))
3165               ]
3166               (const_string "DF")))])
3167
3168 (define_insn "*movsf_internal"
3169   [(set (match_operand:SF 0 "nonimmediate_operand"
3170           "=f,m,f,?r ,?m,x,x,x,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
3171         (match_operand:SF 1 "general_operand"
3172           "fm,f,G,rmF,Fr,C,x,m,x,m  ,*y,*y ,r  ,Yi,r   ,*Ym"))]
3173   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3174    && (!can_create_pseudo_p ()
3175        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3176        || GET_CODE (operands[1]) != CONST_DOUBLE
3177        || (optimize_function_for_size_p (cfun)
3178            && ((!TARGET_SSE_MATH
3179                 && standard_80387_constant_p (operands[1]) > 0)
3180                || (TARGET_SSE_MATH
3181                    && standard_sse_constant_p (operands[1]))))
3182        || memory_operand (operands[0], SFmode))"
3183 {
3184   switch (which_alternative)
3185     {
3186     case 0:
3187     case 1:
3188       return output_387_reg_move (insn, operands);
3189
3190     case 2:
3191       return standard_80387_constant_opcode (operands[1]);
3192
3193     case 3:
3194     case 4:
3195       return "mov{l}\t{%1, %0|%0, %1}";
3196
3197     case 5:
3198       return standard_sse_constant_opcode (insn, operands[1]);
3199
3200     case 6:
3201       if (get_attr_mode (insn) == MODE_V4SF)
3202         return "%vmovaps\t{%1, %0|%0, %1}";
3203       if (TARGET_AVX)
3204         return "vmovss\t{%1, %0, %0|%0, %0, %1}";
3205
3206     case 7:
3207     case 8:
3208       return "%vmovss\t{%1, %0|%0, %1}";
3209
3210     case 9:
3211     case 10:
3212     case 14:
3213     case 15:
3214       return "movd\t{%1, %0|%0, %1}";
3215
3216     case 11:
3217       return "movq\t{%1, %0|%0, %1}";
3218
3219     case 12:
3220     case 13:
3221       return "%vmovd\t{%1, %0|%0, %1}";
3222
3223     default:
3224       gcc_unreachable ();
3225     }
3226 }
3227   [(set (attr "type")
3228         (cond [(eq_attr "alternative" "0,1,2")
3229                  (const_string "fmov")
3230                (eq_attr "alternative" "3,4")
3231                  (const_string "multi")
3232                (eq_attr "alternative" "5")
3233                  (const_string "sselog1")
3234                (eq_attr "alternative" "9,10,11,14,15")
3235                  (const_string "mmxmov")
3236               ]
3237               (const_string "ssemov")))
3238    (set (attr "prefix")
3239      (if_then_else (eq_attr "alternative" "5,6,7,8,12,13")
3240        (const_string "maybe_vex")
3241        (const_string "orig")))
3242    (set (attr "mode")
3243         (cond [(eq_attr "alternative" "3,4,9,10")
3244                  (const_string "SI")
3245                (eq_attr "alternative" "5")
3246                  (if_then_else
3247                    (and (and (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3248                              (match_test "TARGET_SSE2"))
3249                         (not (match_test "optimize_function_for_size_p (cfun)")))
3250                    (const_string "TI")
3251                    (const_string "V4SF"))
3252                /* For architectures resolving dependencies on
3253                   whole SSE registers use APS move to break dependency
3254                   chains, otherwise use short move to avoid extra work.
3255
3256                   Do the same for architectures resolving dependencies on
3257                   the parts.  While in DF mode it is better to always handle
3258                   just register parts, the SF mode is different due to lack
3259                   of instructions to load just part of the register.  It is
3260                   better to maintain the whole registers in single format
3261                   to avoid problems on using packed logical operations.  */
3262                (eq_attr "alternative" "6")
3263                  (if_then_else
3264                    (ior (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3265                         (match_test "TARGET_SSE_SPLIT_REGS"))
3266                    (const_string "V4SF")
3267                    (const_string "SF"))
3268                (eq_attr "alternative" "11")
3269                  (const_string "DI")]
3270                (const_string "SF")))])
3271
3272 (define_split
3273   [(set (match_operand 0 "any_fp_register_operand" "")
3274         (match_operand 1 "memory_operand" ""))]
3275   "reload_completed
3276    && (GET_MODE (operands[0]) == TFmode
3277        || GET_MODE (operands[0]) == XFmode
3278        || GET_MODE (operands[0]) == DFmode
3279        || GET_MODE (operands[0]) == SFmode)
3280    && (operands[2] = find_constant_src (insn))"
3281   [(set (match_dup 0) (match_dup 2))]
3282 {
3283   rtx c = operands[2];
3284   int r = REGNO (operands[0]);
3285
3286   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3287       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3288     FAIL;
3289 })
3290
3291 (define_split
3292   [(set (match_operand 0 "any_fp_register_operand" "")
3293         (float_extend (match_operand 1 "memory_operand" "")))]
3294   "reload_completed
3295    && (GET_MODE (operands[0]) == TFmode
3296        || GET_MODE (operands[0]) == XFmode
3297        || GET_MODE (operands[0]) == DFmode)
3298    && (operands[2] = find_constant_src (insn))"
3299   [(set (match_dup 0) (match_dup 2))]
3300 {
3301   rtx c = operands[2];
3302   int r = REGNO (operands[0]);
3303
3304   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3305       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3306     FAIL;
3307 })
3308
3309 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3310 (define_split
3311   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
3312         (match_operand:X87MODEF 1 "immediate_operand" ""))]
3313   "reload_completed
3314    && (standard_80387_constant_p (operands[1]) == 8
3315        || standard_80387_constant_p (operands[1]) == 9)"
3316   [(set (match_dup 0)(match_dup 1))
3317    (set (match_dup 0)
3318         (neg:X87MODEF (match_dup 0)))]
3319 {
3320   REAL_VALUE_TYPE r;
3321
3322   REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3323   if (real_isnegzero (&r))
3324     operands[1] = CONST0_RTX (<MODE>mode);
3325   else
3326     operands[1] = CONST1_RTX (<MODE>mode);
3327 })
3328
3329 (define_split
3330   [(set (match_operand 0 "nonimmediate_operand" "")
3331         (match_operand 1 "general_operand" ""))]
3332   "reload_completed
3333    && (GET_MODE (operands[0]) == TFmode
3334        || GET_MODE (operands[0]) == XFmode
3335        || GET_MODE (operands[0]) == DFmode)
3336    && !(ANY_FP_REG_P (operands[0]) || ANY_FP_REG_P (operands[1]))"
3337   [(const_int 0)]
3338   "ix86_split_long_move (operands); DONE;")
3339
3340 (define_insn "swapxf"
3341   [(set (match_operand:XF 0 "register_operand" "+f")
3342         (match_operand:XF 1 "register_operand" "+f"))
3343    (set (match_dup 1)
3344         (match_dup 0))]
3345   "TARGET_80387"
3346 {
3347   if (STACK_TOP_P (operands[0]))
3348     return "fxch\t%1";
3349   else
3350     return "fxch\t%0";
3351 }
3352   [(set_attr "type" "fxch")
3353    (set_attr "mode" "XF")])
3354
3355 (define_insn "*swap<mode>"
3356   [(set (match_operand:MODEF 0 "fp_register_operand" "+f")
3357         (match_operand:MODEF 1 "fp_register_operand" "+f"))
3358    (set (match_dup 1)
3359         (match_dup 0))]
3360   "TARGET_80387 || reload_completed"
3361 {
3362   if (STACK_TOP_P (operands[0]))
3363     return "fxch\t%1";
3364   else
3365     return "fxch\t%0";
3366 }
3367   [(set_attr "type" "fxch")
3368    (set_attr "mode" "<MODE>")])
3369 \f
3370 ;; Zero extension instructions
3371
3372 (define_expand "zero_extendsidi2"
3373   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3374         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3375   ""
3376 {
3377   if (!TARGET_64BIT)
3378     {
3379       emit_insn (gen_zero_extendsidi2_1 (operands[0], operands[1]));
3380       DONE;
3381     }
3382 })
3383
3384 (define_insn "*zero_extendsidi2_rex64"
3385   [(set (match_operand:DI 0 "nonimmediate_operand"  "=r,o,?*Ym,?*y,?*Yi,*x")
3386         (zero_extend:DI
3387          (match_operand:SI 1 "nonimmediate_operand" "rm,0,r   ,m  ,r   ,m")))]
3388   "TARGET_64BIT"
3389   "@
3390    mov{l}\t{%1, %k0|%k0, %1}
3391    #
3392    movd\t{%1, %0|%0, %1}
3393    movd\t{%1, %0|%0, %1}
3394    %vmovd\t{%1, %0|%0, %1}
3395    %vmovd\t{%1, %0|%0, %1}"
3396   [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
3397    (set_attr "prefix" "orig,*,orig,orig,maybe_vex,maybe_vex")
3398    (set_attr "prefix_0f" "0,*,*,*,*,*")
3399    (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
3400
3401 (define_split
3402   [(set (match_operand:DI 0 "memory_operand" "")
3403         (zero_extend:DI (match_dup 0)))]
3404   "TARGET_64BIT"
3405   [(set (match_dup 4) (const_int 0))]
3406   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3407
3408 ;; %%% Kill me once multi-word ops are sane.
3409 (define_insn "zero_extendsidi2_1"
3410   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*x")
3411         (zero_extend:DI
3412          (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r   ,m  ,r   ,m")))
3413    (clobber (reg:CC FLAGS_REG))]
3414   "!TARGET_64BIT"
3415   "@
3416    #
3417    #
3418    #
3419    movd\t{%1, %0|%0, %1}
3420    movd\t{%1, %0|%0, %1}
3421    %vmovd\t{%1, %0|%0, %1}
3422    %vmovd\t{%1, %0|%0, %1}"
3423   [(set_attr "isa" "*,*,*,*,*,*,sse2")
3424    (set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")
3425    (set_attr "prefix" "*,*,*,orig,orig,maybe_vex,maybe_vex")
3426    (set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")])
3427
3428 (define_split
3429   [(set (match_operand:DI 0 "register_operand" "")
3430         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3431    (clobber (reg:CC FLAGS_REG))]
3432   "!TARGET_64BIT && reload_completed
3433    && true_regnum (operands[0]) == true_regnum (operands[1])"
3434   [(set (match_dup 4) (const_int 0))]
3435   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3436
3437 (define_split
3438   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3439         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3440    (clobber (reg:CC FLAGS_REG))]
3441   "!TARGET_64BIT && reload_completed
3442    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))"
3443   [(set (match_dup 3) (match_dup 1))
3444    (set (match_dup 4) (const_int 0))]
3445   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3446
3447 (define_insn "zero_extend<mode>di2"
3448   [(set (match_operand:DI 0 "register_operand" "=r")
3449         (zero_extend:DI
3450          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3451   "TARGET_64BIT"
3452   "movz{<imodesuffix>l|x}\t{%1, %k0|%k0, %1}"
3453   [(set_attr "type" "imovx")
3454    (set_attr "mode" "SI")])
3455
3456 (define_expand "zero_extendhisi2"
3457   [(set (match_operand:SI 0 "register_operand" "")
3458         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3459   ""
3460 {
3461   if (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3462     {
3463       operands[1] = force_reg (HImode, operands[1]);
3464       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3465       DONE;
3466     }
3467 })
3468
3469 (define_insn_and_split "zero_extendhisi2_and"
3470   [(set (match_operand:SI 0 "register_operand" "=r")
3471         (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3472    (clobber (reg:CC FLAGS_REG))]
3473   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3474   "#"
3475   "&& reload_completed"
3476   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3477               (clobber (reg:CC FLAGS_REG))])]
3478   ""
3479   [(set_attr "type" "alu1")
3480    (set_attr "mode" "SI")])
3481
3482 (define_insn "*zero_extendhisi2_movzwl"
3483   [(set (match_operand:SI 0 "register_operand" "=r")
3484         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3485   "!TARGET_ZERO_EXTEND_WITH_AND
3486    || optimize_function_for_size_p (cfun)"
3487   "movz{wl|x}\t{%1, %0|%0, %1}"
3488   [(set_attr "type" "imovx")
3489    (set_attr "mode" "SI")])
3490
3491 (define_expand "zero_extendqi<mode>2"
3492   [(parallel
3493     [(set (match_operand:SWI24 0 "register_operand" "")
3494           (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3495      (clobber (reg:CC FLAGS_REG))])])
3496
3497 (define_insn "*zero_extendqi<mode>2_and"
3498   [(set (match_operand:SWI24 0 "register_operand" "=r,?&q")
3499         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3500    (clobber (reg:CC FLAGS_REG))]
3501   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3502   "#"
3503   [(set_attr "type" "alu1")
3504    (set_attr "mode" "<MODE>")])
3505
3506 ;; When source and destination does not overlap, clear destination
3507 ;; first and then do the movb
3508 (define_split
3509   [(set (match_operand:SWI24 0 "register_operand" "")
3510         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3511    (clobber (reg:CC FLAGS_REG))]
3512   "reload_completed
3513    && (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3514    && ANY_QI_REG_P (operands[0])
3515    && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
3516    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3517   [(set (strict_low_part (match_dup 2)) (match_dup 1))]
3518 {
3519   operands[2] = gen_lowpart (QImode, operands[0]);
3520   ix86_expand_clear (operands[0]);
3521 })
3522
3523 (define_insn "*zero_extendqi<mode>2_movzbl_and"
3524   [(set (match_operand:SWI24 0 "register_operand" "=r,r")
3525         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3526    (clobber (reg:CC FLAGS_REG))]
3527   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun)"
3528   "#"
3529   [(set_attr "type" "imovx,alu1")
3530    (set_attr "mode" "<MODE>")])
3531
3532 ;; For the movzbl case strip only the clobber
3533 (define_split
3534   [(set (match_operand:SWI24 0 "register_operand" "")
3535         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3536    (clobber (reg:CC FLAGS_REG))]
3537   "reload_completed
3538    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
3539    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3540   [(set (match_dup 0)
3541         (zero_extend:SWI24 (match_dup 1)))])
3542
3543 ; zero extend to SImode to avoid partial register stalls
3544 (define_insn "*zero_extendqi<mode>2_movzbl"
3545   [(set (match_operand:SWI24 0 "register_operand" "=r")
3546         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3547   "reload_completed
3548    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
3549   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3550   [(set_attr "type" "imovx")
3551    (set_attr "mode" "SI")])
3552
3553 ;; Rest is handled by single and.
3554 (define_split
3555   [(set (match_operand:SWI24 0 "register_operand" "")
3556         (zero_extend:SWI24 (match_operand:QI 1 "register_operand" "")))
3557    (clobber (reg:CC FLAGS_REG))]
3558   "reload_completed
3559    && true_regnum (operands[0]) == true_regnum (operands[1])"
3560   [(parallel [(set (match_dup 0) (and:SWI24 (match_dup 0) (const_int 255)))
3561               (clobber (reg:CC FLAGS_REG))])])
3562 \f
3563 ;; Sign extension instructions
3564
3565 (define_expand "extendsidi2"
3566   [(set (match_operand:DI 0 "register_operand" "")
3567         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))]
3568   ""
3569 {
3570   if (!TARGET_64BIT)
3571     {
3572       emit_insn (gen_extendsidi2_1 (operands[0], operands[1]));
3573       DONE;
3574     }
3575 })
3576
3577 (define_insn "*extendsidi2_rex64"
3578   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3579         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3580   "TARGET_64BIT"
3581   "@
3582    {cltq|cdqe}
3583    movs{lq|x}\t{%1, %0|%0, %1}"
3584   [(set_attr "type" "imovx")
3585    (set_attr "mode" "DI")
3586    (set_attr "prefix_0f" "0")
3587    (set_attr "modrm" "0,1")])
3588
3589 (define_insn "extendsidi2_1"
3590   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3591         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3592    (clobber (reg:CC FLAGS_REG))
3593    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3594   "!TARGET_64BIT"
3595   "#")
3596
3597 ;; Extend to memory case when source register does die.
3598 (define_split
3599   [(set (match_operand:DI 0 "memory_operand" "")
3600         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3601    (clobber (reg:CC FLAGS_REG))
3602    (clobber (match_operand:SI 2 "register_operand" ""))]
3603   "(reload_completed
3604     && dead_or_set_p (insn, operands[1])
3605     && !reg_mentioned_p (operands[1], operands[0]))"
3606   [(set (match_dup 3) (match_dup 1))
3607    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3608               (clobber (reg:CC FLAGS_REG))])
3609    (set (match_dup 4) (match_dup 1))]
3610   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3611
3612 ;; Extend to memory case when source register does not die.
3613 (define_split
3614   [(set (match_operand:DI 0 "memory_operand" "")
3615         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3616    (clobber (reg:CC FLAGS_REG))
3617    (clobber (match_operand:SI 2 "register_operand" ""))]
3618   "reload_completed"
3619   [(const_int 0)]
3620 {
3621   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3622
3623   emit_move_insn (operands[3], operands[1]);
3624
3625   /* Generate a cltd if possible and doing so it profitable.  */
3626   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3627       && true_regnum (operands[1]) == AX_REG
3628       && true_regnum (operands[2]) == DX_REG)
3629     {
3630       emit_insn (gen_ashrsi3_cvt (operands[2], operands[1], GEN_INT (31)));
3631     }
3632   else
3633     {
3634       emit_move_insn (operands[2], operands[1]);
3635       emit_insn (gen_ashrsi3_cvt (operands[2], operands[2], GEN_INT (31)));
3636     }
3637   emit_move_insn (operands[4], operands[2]);
3638   DONE;
3639 })
3640
3641 ;; Extend to register case.  Optimize case where source and destination
3642 ;; registers match and cases where we can use cltd.
3643 (define_split
3644   [(set (match_operand:DI 0 "register_operand" "")
3645         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3646    (clobber (reg:CC FLAGS_REG))
3647    (clobber (match_scratch:SI 2 ""))]
3648   "reload_completed"
3649   [(const_int 0)]
3650 {
3651   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3652
3653   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3654     emit_move_insn (operands[3], operands[1]);
3655
3656   /* Generate a cltd if possible and doing so it profitable.  */
3657   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3658       && true_regnum (operands[3]) == AX_REG
3659       && true_regnum (operands[4]) == DX_REG)
3660     {
3661       emit_insn (gen_ashrsi3_cvt (operands[4], operands[3], GEN_INT (31)));
3662       DONE;
3663     }
3664
3665   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3666     emit_move_insn (operands[4], operands[1]);
3667
3668   emit_insn (gen_ashrsi3_cvt (operands[4], operands[4], GEN_INT (31)));
3669   DONE;
3670 })
3671
3672 (define_insn "extend<mode>di2"
3673   [(set (match_operand:DI 0 "register_operand" "=r")
3674         (sign_extend:DI
3675          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3676   "TARGET_64BIT"
3677   "movs{<imodesuffix>q|x}\t{%1, %0|%0, %1}"
3678   [(set_attr "type" "imovx")
3679    (set_attr "mode" "DI")])
3680
3681 (define_insn "extendhisi2"
3682   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3683         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3684   ""
3685 {
3686   switch (get_attr_prefix_0f (insn))
3687     {
3688     case 0:
3689       return "{cwtl|cwde}";
3690     default:
3691       return "movs{wl|x}\t{%1, %0|%0, %1}";
3692     }
3693 }
3694   [(set_attr "type" "imovx")
3695    (set_attr "mode" "SI")
3696    (set (attr "prefix_0f")
3697      ;; movsx is short decodable while cwtl is vector decoded.
3698      (if_then_else (and (eq_attr "cpu" "!k6")
3699                         (eq_attr "alternative" "0"))
3700         (const_string "0")
3701         (const_string "1")))
3702    (set (attr "modrm")
3703      (if_then_else (eq_attr "prefix_0f" "0")
3704         (const_string "0")
3705         (const_string "1")))])
3706
3707 (define_insn "*extendhisi2_zext"
3708   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3709         (zero_extend:DI
3710          (sign_extend:SI
3711           (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3712   "TARGET_64BIT"
3713 {
3714   switch (get_attr_prefix_0f (insn))
3715     {
3716     case 0:
3717       return "{cwtl|cwde}";
3718     default:
3719       return "movs{wl|x}\t{%1, %k0|%k0, %1}";
3720     }
3721 }
3722   [(set_attr "type" "imovx")
3723    (set_attr "mode" "SI")
3724    (set (attr "prefix_0f")
3725      ;; movsx is short decodable while cwtl is vector decoded.
3726      (if_then_else (and (eq_attr "cpu" "!k6")
3727                         (eq_attr "alternative" "0"))
3728         (const_string "0")
3729         (const_string "1")))
3730    (set (attr "modrm")
3731      (if_then_else (eq_attr "prefix_0f" "0")
3732         (const_string "0")
3733         (const_string "1")))])
3734
3735 (define_insn "extendqisi2"
3736   [(set (match_operand:SI 0 "register_operand" "=r")
3737         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3738   ""
3739   "movs{bl|x}\t{%1, %0|%0, %1}"
3740    [(set_attr "type" "imovx")
3741     (set_attr "mode" "SI")])
3742
3743 (define_insn "*extendqisi2_zext"
3744   [(set (match_operand:DI 0 "register_operand" "=r")
3745         (zero_extend:DI
3746           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3747   "TARGET_64BIT"
3748   "movs{bl|x}\t{%1, %k0|%k0, %1}"
3749    [(set_attr "type" "imovx")
3750     (set_attr "mode" "SI")])
3751
3752 (define_insn "extendqihi2"
3753   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3754         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3755   ""
3756 {
3757   switch (get_attr_prefix_0f (insn))
3758     {
3759     case 0:
3760       return "{cbtw|cbw}";
3761     default:
3762       return "movs{bw|x}\t{%1, %0|%0, %1}";
3763     }
3764 }
3765   [(set_attr "type" "imovx")
3766    (set_attr "mode" "HI")
3767    (set (attr "prefix_0f")
3768      ;; movsx is short decodable while cwtl is vector decoded.
3769      (if_then_else (and (eq_attr "cpu" "!k6")
3770                         (eq_attr "alternative" "0"))
3771         (const_string "0")
3772         (const_string "1")))
3773    (set (attr "modrm")
3774      (if_then_else (eq_attr "prefix_0f" "0")
3775         (const_string "0")
3776         (const_string "1")))])
3777 \f
3778 ;; Conversions between float and double.
3779
3780 ;; These are all no-ops in the model used for the 80387.
3781 ;; So just emit moves.
3782
3783 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3784 (define_split
3785   [(set (match_operand:DF 0 "push_operand" "")
3786         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3787   "reload_completed"
3788   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
3789    (set (mem:DF (reg:P SP_REG)) (float_extend:DF (match_dup 1)))])
3790
3791 (define_split
3792   [(set (match_operand:XF 0 "push_operand" "")
3793         (float_extend:XF (match_operand:MODEF 1 "fp_register_operand" "")))]
3794   "reload_completed"
3795   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3796    (set (mem:XF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
3797   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
3798
3799 (define_expand "extendsfdf2"
3800   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3801         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3802   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3803 {
3804   /* ??? Needed for compress_float_constant since all fp constants
3805      are TARGET_LEGITIMATE_CONSTANT_P.  */
3806   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3807     {
3808       if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
3809           && standard_80387_constant_p (operands[1]) > 0)
3810         {
3811           operands[1] = simplify_const_unary_operation
3812             (FLOAT_EXTEND, DFmode, operands[1], SFmode);
3813           emit_move_insn_1 (operands[0], operands[1]);
3814           DONE;
3815         }
3816       operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3817     }
3818 })
3819
3820 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
3821    cvtss2sd:
3822       unpcklps xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3823       cvtps2pd xmm2,xmm1
3824    We do the conversion post reload to avoid producing of 128bit spills
3825    that might lead to ICE on 32bit target.  The sequence unlikely combine
3826    anyway.  */
3827 (define_split
3828   [(set (match_operand:DF 0 "register_operand" "")
3829         (float_extend:DF
3830           (match_operand:SF 1 "nonimmediate_operand" "")))]
3831   "TARGET_USE_VECTOR_FP_CONVERTS
3832    && optimize_insn_for_speed_p ()
3833    && reload_completed && SSE_REG_P (operands[0])"
3834    [(set (match_dup 2)
3835          (float_extend:V2DF
3836            (vec_select:V2SF
3837              (match_dup 3)
3838              (parallel [(const_int 0) (const_int 1)]))))]
3839 {
3840   operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
3841   operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
3842   /* Use movss for loading from memory, unpcklps reg, reg for registers.
3843      Try to avoid move when unpacking can be done in source.  */
3844   if (REG_P (operands[1]))
3845     {
3846       /* If it is unsafe to overwrite upper half of source, we need
3847          to move to destination and unpack there.  */
3848       if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
3849            || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
3850           && true_regnum (operands[0]) != true_regnum (operands[1]))
3851         {
3852           rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
3853           emit_move_insn (tmp, operands[1]);
3854         }
3855       else
3856         operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
3857       emit_insn (gen_vec_interleave_lowv4sf (operands[3], operands[3],
3858                                              operands[3]));
3859     }
3860   else
3861     emit_insn (gen_vec_setv4sf_0 (operands[3],
3862                                   CONST0_RTX (V4SFmode), operands[1]));
3863 })
3864
3865 (define_insn "*extendsfdf2_mixed"
3866   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
3867         (float_extend:DF
3868           (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
3869   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3870 {
3871   switch (which_alternative)
3872     {
3873     case 0:
3874     case 1:
3875       return output_387_reg_move (insn, operands);
3876
3877     case 2:
3878       return "%vcvtss2sd\t{%1, %d0|%d0, %1}";
3879
3880     default:
3881       gcc_unreachable ();
3882     }
3883 }
3884   [(set_attr "type" "fmov,fmov,ssecvt")
3885    (set_attr "prefix" "orig,orig,maybe_vex")
3886    (set_attr "mode" "SF,XF,DF")])
3887
3888 (define_insn "*extendsfdf2_sse"
3889   [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
3890         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
3891   "TARGET_SSE2 && TARGET_SSE_MATH"
3892   "%vcvtss2sd\t{%1, %d0|%d0, %1}"
3893   [(set_attr "type" "ssecvt")
3894    (set_attr "prefix" "maybe_vex")
3895    (set_attr "mode" "DF")])
3896
3897 (define_insn "*extendsfdf2_i387"
3898   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3899         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3900   "TARGET_80387"
3901   "* return output_387_reg_move (insn, operands);"
3902   [(set_attr "type" "fmov")
3903    (set_attr "mode" "SF,XF")])
3904
3905 (define_expand "extend<mode>xf2"
3906   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3907         (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
3908   "TARGET_80387"
3909 {
3910   /* ??? Needed for compress_float_constant since all fp constants
3911      are TARGET_LEGITIMATE_CONSTANT_P.  */
3912   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3913     {
3914       if (standard_80387_constant_p (operands[1]) > 0)
3915         {
3916           operands[1] = simplify_const_unary_operation
3917             (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
3918           emit_move_insn_1 (operands[0], operands[1]);
3919           DONE;
3920         }
3921       operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
3922     }
3923 })
3924
3925 (define_insn "*extend<mode>xf2_i387"
3926   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3927         (float_extend:XF
3928           (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
3929   "TARGET_80387"
3930   "* return output_387_reg_move (insn, operands);"
3931   [(set_attr "type" "fmov")
3932    (set_attr "mode" "<MODE>,XF")])
3933
3934 ;; %%% This seems bad bad news.
3935 ;; This cannot output into an f-reg because there is no way to be sure
3936 ;; of truncating in that case.  Otherwise this is just like a simple move
3937 ;; insn.  So we pretend we can output to a reg in order to get better
3938 ;; register preferencing, but we really use a stack slot.
3939
3940 ;; Conversion from DFmode to SFmode.
3941
3942 (define_expand "truncdfsf2"
3943   [(set (match_operand:SF 0 "nonimmediate_operand" "")
3944         (float_truncate:SF
3945           (match_operand:DF 1 "nonimmediate_operand" "")))]
3946   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3947 {
3948   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3949     ;
3950   else if (flag_unsafe_math_optimizations)
3951     ;
3952   else
3953     {
3954       enum ix86_stack_slot slot = (virtuals_instantiated
3955                                    ? SLOT_TEMP
3956                                    : SLOT_VIRTUAL);
3957       rtx temp = assign_386_stack_local (SFmode, slot);
3958       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3959       DONE;
3960     }
3961 })
3962
3963 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
3964    cvtsd2ss:
3965       unpcklpd xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3966       cvtpd2ps xmm2,xmm1
3967    We do the conversion post reload to avoid producing of 128bit spills
3968    that might lead to ICE on 32bit target.  The sequence unlikely combine
3969    anyway.  */
3970 (define_split
3971   [(set (match_operand:SF 0 "register_operand" "")
3972         (float_truncate:SF
3973           (match_operand:DF 1 "nonimmediate_operand" "")))]
3974   "TARGET_USE_VECTOR_FP_CONVERTS
3975    && optimize_insn_for_speed_p ()
3976    && reload_completed && SSE_REG_P (operands[0])"
3977    [(set (match_dup 2)
3978          (vec_concat:V4SF
3979            (float_truncate:V2SF
3980              (match_dup 4))
3981            (match_dup 3)))]
3982 {
3983   operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
3984   operands[3] = CONST0_RTX (V2SFmode);
3985   operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
3986   /* Use movsd for loading from memory, unpcklpd for registers.
3987      Try to avoid move when unpacking can be done in source, or SSE3
3988      movddup is available.  */
3989   if (REG_P (operands[1]))
3990     {
3991       if (!TARGET_SSE3
3992           && true_regnum (operands[0]) != true_regnum (operands[1])
3993           && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
3994               || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
3995         {
3996           rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
3997           emit_move_insn (tmp, operands[1]);
3998           operands[1] = tmp;
3999         }
4000       else if (!TARGET_SSE3)
4001         operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4002       emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4003     }
4004   else
4005     emit_insn (gen_sse2_loadlpd (operands[4],
4006                                  CONST0_RTX (V2DFmode), operands[1]));
4007 })
4008
4009 (define_expand "truncdfsf2_with_temp"
4010   [(parallel [(set (match_operand:SF 0 "" "")
4011                    (float_truncate:SF (match_operand:DF 1 "" "")))
4012               (clobber (match_operand:SF 2 "" ""))])])
4013
4014 (define_insn "*truncdfsf_fast_mixed"
4015   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm,x")
4016         (float_truncate:SF
4017           (match_operand:DF 1 "nonimmediate_operand" "f  ,xm")))]
4018   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4019 {
4020   switch (which_alternative)
4021     {
4022     case 0:
4023       return output_387_reg_move (insn, operands);
4024     case 1:
4025       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4026     default:
4027       gcc_unreachable ();
4028     }
4029 }
4030   [(set_attr "type" "fmov,ssecvt")
4031    (set_attr "prefix" "orig,maybe_vex")
4032    (set_attr "mode" "SF")])
4033
4034 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4035 ;; because nothing we do here is unsafe.
4036 (define_insn "*truncdfsf_fast_sse"
4037   [(set (match_operand:SF 0 "nonimmediate_operand"   "=x")
4038         (float_truncate:SF
4039           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4040   "TARGET_SSE2 && TARGET_SSE_MATH"
4041   "%vcvtsd2ss\t{%1, %d0|%d0, %1}"
4042   [(set_attr "type" "ssecvt")
4043    (set_attr "prefix" "maybe_vex")
4044    (set_attr "mode" "SF")])
4045
4046 (define_insn "*truncdfsf_fast_i387"
4047   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
4048         (float_truncate:SF
4049           (match_operand:DF 1 "nonimmediate_operand" "f")))]
4050   "TARGET_80387 && flag_unsafe_math_optimizations"
4051   "* return output_387_reg_move (insn, operands);"
4052   [(set_attr "type" "fmov")
4053    (set_attr "mode" "SF")])
4054
4055 (define_insn "*truncdfsf_mixed"
4056   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,x ,?f,?x,?*r")
4057         (float_truncate:SF
4058           (match_operand:DF 1 "nonimmediate_operand" "f ,xm,f ,f ,f")))
4059    (clobber (match_operand:SF 2 "memory_operand"     "=X,X ,m ,m ,m"))]
4060   "TARGET_MIX_SSE_I387"
4061 {
4062   switch (which_alternative)
4063     {
4064     case 0:
4065       return output_387_reg_move (insn, operands);
4066     case 1:
4067       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4068
4069     default:
4070       return "#";
4071     }
4072 }
4073   [(set_attr "isa" "*,sse2,*,*,*")
4074    (set_attr "type" "fmov,ssecvt,multi,multi,multi")
4075    (set_attr "unit" "*,*,i387,i387,i387")
4076    (set_attr "prefix" "orig,maybe_vex,orig,orig,orig")
4077    (set_attr "mode" "SF")])
4078
4079 (define_insn "*truncdfsf_i387"
4080   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?f,?x,?*r")
4081         (float_truncate:SF
4082           (match_operand:DF 1 "nonimmediate_operand" "f ,f ,f ,f")))
4083    (clobber (match_operand:SF 2 "memory_operand"     "=X,m ,m ,m"))]
4084   "TARGET_80387"
4085 {
4086   switch (which_alternative)
4087     {
4088     case 0:
4089       return output_387_reg_move (insn, operands);
4090
4091     default:
4092       return "#";
4093     }
4094 }
4095   [(set_attr "type" "fmov,multi,multi,multi")
4096    (set_attr "unit" "*,i387,i387,i387")
4097    (set_attr "mode" "SF")])
4098
4099 (define_insn "*truncdfsf2_i387_1"
4100   [(set (match_operand:SF 0 "memory_operand" "=m")
4101         (float_truncate:SF
4102           (match_operand:DF 1 "register_operand" "f")))]
4103   "TARGET_80387
4104    && !(TARGET_SSE2 && TARGET_SSE_MATH)
4105    && !TARGET_MIX_SSE_I387"
4106   "* return output_387_reg_move (insn, operands);"
4107   [(set_attr "type" "fmov")
4108    (set_attr "mode" "SF")])
4109
4110 (define_split
4111   [(set (match_operand:SF 0 "register_operand" "")
4112         (float_truncate:SF
4113          (match_operand:DF 1 "fp_register_operand" "")))
4114    (clobber (match_operand 2 "" ""))]
4115   "reload_completed"
4116   [(set (match_dup 2) (match_dup 1))
4117    (set (match_dup 0) (match_dup 2))]
4118   "operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));")
4119
4120 ;; Conversion from XFmode to {SF,DF}mode
4121
4122 (define_expand "truncxf<mode>2"
4123   [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4124                    (float_truncate:MODEF
4125                      (match_operand:XF 1 "register_operand" "")))
4126               (clobber (match_dup 2))])]
4127   "TARGET_80387"
4128 {
4129   if (flag_unsafe_math_optimizations)
4130     {
4131       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4132       emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4133       if (reg != operands[0])
4134         emit_move_insn (operands[0], reg);
4135       DONE;
4136     }
4137   else
4138     {
4139       enum ix86_stack_slot slot = (virtuals_instantiated
4140                                    ? SLOT_TEMP
4141                                    : SLOT_VIRTUAL);
4142       operands[2] = assign_386_stack_local (<MODE>mode, slot);
4143     }
4144 })
4145
4146 (define_insn "*truncxfsf2_mixed"
4147   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4148         (float_truncate:SF
4149           (match_operand:XF 1 "register_operand"   "f ,f ,f ,f")))
4150    (clobber (match_operand:SF 2 "memory_operand"   "=X,m ,m ,m"))]
4151   "TARGET_80387"
4152 {
4153   gcc_assert (!which_alternative);
4154   return output_387_reg_move (insn, operands);
4155 }
4156   [(set_attr "type" "fmov,multi,multi,multi")
4157    (set_attr "unit" "*,i387,i387,i387")
4158    (set_attr "mode" "SF")])
4159
4160 (define_insn "*truncxfdf2_mixed"
4161   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4162         (float_truncate:DF
4163           (match_operand:XF 1 "register_operand"   "f ,f ,f  ,f")))
4164    (clobber (match_operand:DF 2 "memory_operand"   "=X,m ,m  ,m"))]
4165   "TARGET_80387"
4166 {
4167   gcc_assert (!which_alternative);
4168   return output_387_reg_move (insn, operands);
4169 }
4170   [(set_attr "isa" "*,*,sse2,*")
4171    (set_attr "type" "fmov,multi,multi,multi")
4172    (set_attr "unit" "*,i387,i387,i387")
4173    (set_attr "mode" "DF")])
4174
4175 (define_insn "truncxf<mode>2_i387_noop"
4176   [(set (match_operand:MODEF 0 "register_operand" "=f")
4177         (float_truncate:MODEF
4178           (match_operand:XF 1 "register_operand" "f")))]
4179   "TARGET_80387 && flag_unsafe_math_optimizations"
4180   "* return output_387_reg_move (insn, operands);"
4181   [(set_attr "type" "fmov")
4182    (set_attr "mode" "<MODE>")])
4183
4184 (define_insn "*truncxf<mode>2_i387"
4185   [(set (match_operand:MODEF 0 "memory_operand" "=m")
4186         (float_truncate:MODEF
4187           (match_operand:XF 1 "register_operand" "f")))]
4188   "TARGET_80387"
4189   "* return output_387_reg_move (insn, operands);"
4190   [(set_attr "type" "fmov")
4191    (set_attr "mode" "<MODE>")])
4192
4193 (define_split
4194   [(set (match_operand:MODEF 0 "register_operand" "")
4195         (float_truncate:MODEF
4196           (match_operand:XF 1 "register_operand" "")))
4197    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4198   "TARGET_80387 && reload_completed"
4199   [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4200    (set (match_dup 0) (match_dup 2))])
4201
4202 (define_split
4203   [(set (match_operand:MODEF 0 "memory_operand" "")
4204         (float_truncate:MODEF
4205           (match_operand:XF 1 "register_operand" "")))
4206    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4207   "TARGET_80387"
4208   [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))])
4209 \f
4210 ;; Signed conversion to DImode.
4211
4212 (define_expand "fix_truncxfdi2"
4213   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4214                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4215               (clobber (reg:CC FLAGS_REG))])]
4216   "TARGET_80387"
4217 {
4218   if (TARGET_FISTTP)
4219    {
4220      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4221      DONE;
4222    }
4223 })
4224
4225 (define_expand "fix_trunc<mode>di2"
4226   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4227                    (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4228               (clobber (reg:CC FLAGS_REG))])]
4229   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4230 {
4231   if (TARGET_FISTTP
4232       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4233    {
4234      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4235      DONE;
4236    }
4237   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4238    {
4239      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4240      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4241      if (out != operands[0])
4242         emit_move_insn (operands[0], out);
4243      DONE;
4244    }
4245 })
4246
4247 ;; Signed conversion to SImode.
4248
4249 (define_expand "fix_truncxfsi2"
4250   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4251                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4252               (clobber (reg:CC FLAGS_REG))])]
4253   "TARGET_80387"
4254 {
4255   if (TARGET_FISTTP)
4256    {
4257      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4258      DONE;
4259    }
4260 })
4261
4262 (define_expand "fix_trunc<mode>si2"
4263   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4264                    (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4265               (clobber (reg:CC FLAGS_REG))])]
4266   "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4267 {
4268   if (TARGET_FISTTP
4269       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4270    {
4271      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4272      DONE;
4273    }
4274   if (SSE_FLOAT_MODE_P (<MODE>mode))
4275    {
4276      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4277      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4278      if (out != operands[0])
4279         emit_move_insn (operands[0], out);
4280      DONE;
4281    }
4282 })
4283
4284 ;; Signed conversion to HImode.
4285
4286 (define_expand "fix_trunc<mode>hi2"
4287   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4288                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4289               (clobber (reg:CC FLAGS_REG))])]
4290   "TARGET_80387
4291    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4292 {
4293   if (TARGET_FISTTP)
4294    {
4295      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4296      DONE;
4297    }
4298 })
4299
4300 ;; Unsigned conversion to SImode.
4301
4302 (define_expand "fixuns_trunc<mode>si2"
4303   [(parallel
4304     [(set (match_operand:SI 0 "register_operand" "")
4305           (unsigned_fix:SI
4306             (match_operand:MODEF 1 "nonimmediate_operand" "")))
4307      (use (match_dup 2))
4308      (clobber (match_scratch:<ssevecmode> 3 ""))
4309      (clobber (match_scratch:<ssevecmode> 4 ""))])]
4310   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4311 {
4312   enum machine_mode mode = <MODE>mode;
4313   enum machine_mode vecmode = <ssevecmode>mode;
4314   REAL_VALUE_TYPE TWO31r;
4315   rtx two31;
4316
4317   if (optimize_insn_for_size_p ())
4318     FAIL;
4319
4320   real_ldexp (&TWO31r, &dconst1, 31);
4321   two31 = const_double_from_real_value (TWO31r, mode);
4322   two31 = ix86_build_const_vector (vecmode, true, two31);
4323   operands[2] = force_reg (vecmode, two31);
4324 })
4325
4326 (define_insn_and_split "*fixuns_trunc<mode>_1"
4327   [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4328         (unsigned_fix:SI
4329           (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4330    (use (match_operand:<ssevecmode> 4  "nonimmediate_operand" "m,x"))
4331    (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4332    (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4333   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
4334    && optimize_function_for_speed_p (cfun)"
4335   "#"
4336   "&& reload_completed"
4337   [(const_int 0)]
4338 {
4339   ix86_split_convert_uns_si_sse (operands);
4340   DONE;
4341 })
4342
4343 ;; Unsigned conversion to HImode.
4344 ;; Without these patterns, we'll try the unsigned SI conversion which
4345 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4346
4347 (define_expand "fixuns_trunc<mode>hi2"
4348   [(set (match_dup 2)
4349         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4350    (set (match_operand:HI 0 "nonimmediate_operand" "")
4351         (subreg:HI (match_dup 2) 0))]
4352   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4353   "operands[2] = gen_reg_rtx (SImode);")
4354
4355 ;; When SSE is available, it is always faster to use it!
4356 (define_insn "fix_trunc<mode>di_sse"
4357   [(set (match_operand:DI 0 "register_operand" "=r,r")
4358         (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4359   "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4360    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4361   "%vcvtt<ssemodesuffix>2si{q}\t{%1, %0|%0, %1}"
4362   [(set_attr "type" "sseicvt")
4363    (set_attr "prefix" "maybe_vex")
4364    (set_attr "prefix_rex" "1")
4365    (set_attr "mode" "<MODE>")
4366    (set_attr "athlon_decode" "double,vector")
4367    (set_attr "amdfam10_decode" "double,double")
4368    (set_attr "bdver1_decode" "double,double")])
4369
4370 (define_insn "fix_trunc<mode>si_sse"
4371   [(set (match_operand:SI 0 "register_operand" "=r,r")
4372         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4373   "SSE_FLOAT_MODE_P (<MODE>mode)
4374    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4375   "%vcvtt<ssemodesuffix>2si\t{%1, %0|%0, %1}"
4376   [(set_attr "type" "sseicvt")
4377    (set_attr "prefix" "maybe_vex")
4378    (set_attr "mode" "<MODE>")
4379    (set_attr "athlon_decode" "double,vector")
4380    (set_attr "amdfam10_decode" "double,double")
4381    (set_attr "bdver1_decode" "double,double")])
4382
4383 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4384 (define_peephole2
4385   [(set (match_operand:MODEF 0 "register_operand" "")
4386         (match_operand:MODEF 1 "memory_operand" ""))
4387    (set (match_operand:SWI48x 2 "register_operand" "")
4388         (fix:SWI48x (match_dup 0)))]
4389   "TARGET_SHORTEN_X87_SSE
4390    && !(TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ())
4391    && peep2_reg_dead_p (2, operands[0])"
4392   [(set (match_dup 2) (fix:SWI48x (match_dup 1)))])
4393
4394 ;; Avoid vector decoded forms of the instruction.
4395 (define_peephole2
4396   [(match_scratch:DF 2 "x")
4397    (set (match_operand:SWI48x 0 "register_operand" "")
4398         (fix:SWI48x (match_operand:DF 1 "memory_operand" "")))]
4399   "TARGET_SSE2 && TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4400   [(set (match_dup 2) (match_dup 1))
4401    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4402
4403 (define_peephole2
4404   [(match_scratch:SF 2 "x")
4405    (set (match_operand:SWI48x 0 "register_operand" "")
4406         (fix:SWI48x (match_operand:SF 1 "memory_operand" "")))]
4407   "TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4408   [(set (match_dup 2) (match_dup 1))
4409    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4410
4411 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4412   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4413         (fix:SWI248x (match_operand 1 "register_operand" "")))]
4414   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4415    && TARGET_FISTTP
4416    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4417          && (TARGET_64BIT || <MODE>mode != DImode))
4418         && TARGET_SSE_MATH)
4419    && can_create_pseudo_p ()"
4420   "#"
4421   "&& 1"
4422   [(const_int 0)]
4423 {
4424   if (memory_operand (operands[0], VOIDmode))
4425     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4426   else
4427     {
4428       operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4429       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4430                                                             operands[1],
4431                                                             operands[2]));
4432     }
4433   DONE;
4434 }
4435   [(set_attr "type" "fisttp")
4436    (set_attr "mode" "<MODE>")])
4437
4438 (define_insn "fix_trunc<mode>_i387_fisttp"
4439   [(set (match_operand:SWI248x 0 "memory_operand" "=m")
4440         (fix:SWI248x (match_operand 1 "register_operand" "f")))
4441    (clobber (match_scratch:XF 2 "=&1f"))]
4442   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4443    && TARGET_FISTTP
4444    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4445          && (TARGET_64BIT || <MODE>mode != DImode))
4446         && TARGET_SSE_MATH)"
4447   "* return output_fix_trunc (insn, operands, true);"
4448   [(set_attr "type" "fisttp")
4449    (set_attr "mode" "<MODE>")])
4450
4451 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4452   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "=m,?r")
4453         (fix:SWI248x (match_operand 1 "register_operand" "f,f")))
4454    (clobber (match_operand:SWI248x 2 "memory_operand" "=X,m"))
4455    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4456   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4457    && TARGET_FISTTP
4458    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4459         && (TARGET_64BIT || <MODE>mode != DImode))
4460         && TARGET_SSE_MATH)"
4461   "#"
4462   [(set_attr "type" "fisttp")
4463    (set_attr "mode" "<MODE>")])
4464
4465 (define_split
4466   [(set (match_operand:SWI248x 0 "register_operand" "")
4467         (fix:SWI248x (match_operand 1 "register_operand" "")))
4468    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4469    (clobber (match_scratch 3 ""))]
4470   "reload_completed"
4471   [(parallel [(set (match_dup 2) (fix:SWI248x (match_dup 1)))
4472               (clobber (match_dup 3))])
4473    (set (match_dup 0) (match_dup 2))])
4474
4475 (define_split
4476   [(set (match_operand:SWI248x 0 "memory_operand" "")
4477         (fix:SWI248x (match_operand 1 "register_operand" "")))
4478    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4479    (clobber (match_scratch 3 ""))]
4480   "reload_completed"
4481   [(parallel [(set (match_dup 0) (fix:SWI248x (match_dup 1)))
4482               (clobber (match_dup 3))])])
4483
4484 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4485 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4486 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4487 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4488 ;; function in i386.c.
4489 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4490   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4491         (fix:SWI248x (match_operand 1 "register_operand" "")))
4492    (clobber (reg:CC FLAGS_REG))]
4493   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4494    && !TARGET_FISTTP
4495    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4496          && (TARGET_64BIT || <MODE>mode != DImode))
4497    && can_create_pseudo_p ()"
4498   "#"
4499   "&& 1"
4500   [(const_int 0)]
4501 {
4502   ix86_optimize_mode_switching[I387_TRUNC] = 1;
4503
4504   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4505   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4506   if (memory_operand (operands[0], VOIDmode))
4507     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4508                                          operands[2], operands[3]));
4509   else
4510     {
4511       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4512       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4513                                                      operands[2], operands[3],
4514                                                      operands[4]));
4515     }
4516   DONE;
4517 }
4518   [(set_attr "type" "fistp")
4519    (set_attr "i387_cw" "trunc")
4520    (set_attr "mode" "<MODE>")])
4521
4522 (define_insn "fix_truncdi_i387"
4523   [(set (match_operand:DI 0 "memory_operand" "=m")
4524         (fix:DI (match_operand 1 "register_operand" "f")))
4525    (use (match_operand:HI 2 "memory_operand" "m"))
4526    (use (match_operand:HI 3 "memory_operand" "m"))
4527    (clobber (match_scratch:XF 4 "=&1f"))]
4528   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4529    && !TARGET_FISTTP
4530    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4531   "* return output_fix_trunc (insn, operands, false);"
4532   [(set_attr "type" "fistp")
4533    (set_attr "i387_cw" "trunc")
4534    (set_attr "mode" "DI")])
4535
4536 (define_insn "fix_truncdi_i387_with_temp"
4537   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4538         (fix:DI (match_operand 1 "register_operand" "f,f")))
4539    (use (match_operand:HI 2 "memory_operand" "m,m"))
4540    (use (match_operand:HI 3 "memory_operand" "m,m"))
4541    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
4542    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4543   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4544    && !TARGET_FISTTP
4545    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4546   "#"
4547   [(set_attr "type" "fistp")
4548    (set_attr "i387_cw" "trunc")
4549    (set_attr "mode" "DI")])
4550
4551 (define_split
4552   [(set (match_operand:DI 0 "register_operand" "")
4553         (fix:DI (match_operand 1 "register_operand" "")))
4554    (use (match_operand:HI 2 "memory_operand" ""))
4555    (use (match_operand:HI 3 "memory_operand" ""))
4556    (clobber (match_operand:DI 4 "memory_operand" ""))
4557    (clobber (match_scratch 5 ""))]
4558   "reload_completed"
4559   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4560               (use (match_dup 2))
4561               (use (match_dup 3))
4562               (clobber (match_dup 5))])
4563    (set (match_dup 0) (match_dup 4))])
4564
4565 (define_split
4566   [(set (match_operand:DI 0 "memory_operand" "")
4567         (fix:DI (match_operand 1 "register_operand" "")))
4568    (use (match_operand:HI 2 "memory_operand" ""))
4569    (use (match_operand:HI 3 "memory_operand" ""))
4570    (clobber (match_operand:DI 4 "memory_operand" ""))
4571    (clobber (match_scratch 5 ""))]
4572   "reload_completed"
4573   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4574               (use (match_dup 2))
4575               (use (match_dup 3))
4576               (clobber (match_dup 5))])])
4577
4578 (define_insn "fix_trunc<mode>_i387"
4579   [(set (match_operand:SWI24 0 "memory_operand" "=m")
4580         (fix:SWI24 (match_operand 1 "register_operand" "f")))
4581    (use (match_operand:HI 2 "memory_operand" "m"))
4582    (use (match_operand:HI 3 "memory_operand" "m"))]
4583   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4584    && !TARGET_FISTTP
4585    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4586   "* return output_fix_trunc (insn, operands, false);"
4587   [(set_attr "type" "fistp")
4588    (set_attr "i387_cw" "trunc")
4589    (set_attr "mode" "<MODE>")])
4590
4591 (define_insn "fix_trunc<mode>_i387_with_temp"
4592   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
4593         (fix:SWI24 (match_operand 1 "register_operand" "f,f")))
4594    (use (match_operand:HI 2 "memory_operand" "m,m"))
4595    (use (match_operand:HI 3 "memory_operand" "m,m"))
4596    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
4597   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4598    && !TARGET_FISTTP
4599    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4600   "#"
4601   [(set_attr "type" "fistp")
4602    (set_attr "i387_cw" "trunc")
4603    (set_attr "mode" "<MODE>")])
4604
4605 (define_split
4606   [(set (match_operand:SWI24 0 "register_operand" "")
4607         (fix:SWI24 (match_operand 1 "register_operand" "")))
4608    (use (match_operand:HI 2 "memory_operand" ""))
4609    (use (match_operand:HI 3 "memory_operand" ""))
4610    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4611   "reload_completed"
4612   [(parallel [(set (match_dup 4) (fix:SWI24 (match_dup 1)))
4613               (use (match_dup 2))
4614               (use (match_dup 3))])
4615    (set (match_dup 0) (match_dup 4))])
4616
4617 (define_split
4618   [(set (match_operand:SWI24 0 "memory_operand" "")
4619         (fix:SWI24 (match_operand 1 "register_operand" "")))
4620    (use (match_operand:HI 2 "memory_operand" ""))
4621    (use (match_operand:HI 3 "memory_operand" ""))
4622    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4623   "reload_completed"
4624   [(parallel [(set (match_dup 0) (fix:SWI24 (match_dup 1)))
4625               (use (match_dup 2))
4626               (use (match_dup 3))])])
4627
4628 (define_insn "x86_fnstcw_1"
4629   [(set (match_operand:HI 0 "memory_operand" "=m")
4630         (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
4631   "TARGET_80387"
4632   "fnstcw\t%0"
4633   [(set (attr "length")
4634         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4635    (set_attr "mode" "HI")
4636    (set_attr "unit" "i387")
4637    (set_attr "bdver1_decode" "vector")])
4638
4639 (define_insn "x86_fldcw_1"
4640   [(set (reg:HI FPCR_REG)
4641         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4642   "TARGET_80387"
4643   "fldcw\t%0"
4644   [(set (attr "length")
4645         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4646    (set_attr "mode" "HI")
4647    (set_attr "unit" "i387")
4648    (set_attr "athlon_decode" "vector")
4649    (set_attr "amdfam10_decode" "vector")
4650    (set_attr "bdver1_decode" "vector")])
4651 \f
4652 ;; Conversion between fixed point and floating point.
4653
4654 ;; Even though we only accept memory inputs, the backend _really_
4655 ;; wants to be able to do this between registers.
4656
4657 (define_expand "floathi<mode>2"
4658   [(set (match_operand:X87MODEF 0 "register_operand" "")
4659         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
4660   "TARGET_80387
4661    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4662        || TARGET_MIX_SSE_I387)")
4663
4664 ;; Pre-reload splitter to add memory clobber to the pattern.
4665 (define_insn_and_split "*floathi<mode>2_1"
4666   [(set (match_operand:X87MODEF 0 "register_operand" "")
4667         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))]
4668   "TARGET_80387
4669    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4670        || TARGET_MIX_SSE_I387)
4671    && can_create_pseudo_p ()"
4672   "#"
4673   "&& 1"
4674   [(parallel [(set (match_dup 0)
4675               (float:X87MODEF (match_dup 1)))
4676    (clobber (match_dup 2))])]
4677   "operands[2] = assign_386_stack_local (HImode, SLOT_TEMP);")
4678
4679 (define_insn "*floathi<mode>2_i387_with_temp"
4680   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
4681         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))
4682   (clobber (match_operand:HI 2 "memory_operand" "=X,m"))]
4683   "TARGET_80387
4684    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4685        || TARGET_MIX_SSE_I387)"
4686   "#"
4687   [(set_attr "type" "fmov,multi")
4688    (set_attr "mode" "<MODE>")
4689    (set_attr "unit" "*,i387")
4690    (set_attr "fp_int_src" "true")])
4691
4692 (define_insn "*floathi<mode>2_i387"
4693   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
4694         (float:X87MODEF (match_operand:HI 1 "memory_operand" "m")))]
4695   "TARGET_80387
4696    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4697        || TARGET_MIX_SSE_I387)"
4698   "fild%Z1\t%1"
4699   [(set_attr "type" "fmov")
4700    (set_attr "mode" "<MODE>")
4701    (set_attr "fp_int_src" "true")])
4702
4703 (define_split
4704   [(set (match_operand:X87MODEF 0 "register_operand" "")
4705         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))
4706    (clobber (match_operand:HI 2 "memory_operand" ""))]
4707   "TARGET_80387
4708    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4709        || TARGET_MIX_SSE_I387)
4710    && reload_completed"
4711   [(set (match_dup 2) (match_dup 1))
4712    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
4713
4714 (define_split
4715   [(set (match_operand:X87MODEF 0 "register_operand" "")
4716         (float:X87MODEF (match_operand:HI 1 "memory_operand" "")))
4717    (clobber (match_operand:HI 2 "memory_operand" ""))]
4718    "TARGET_80387
4719     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4720         || TARGET_MIX_SSE_I387)
4721     && reload_completed"
4722   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
4723
4724 (define_expand "float<SWI48x:mode><X87MODEF:mode>2"
4725   [(set (match_operand:X87MODEF 0 "register_operand" "")
4726         (float:X87MODEF
4727           (match_operand:SWI48x 1 "nonimmediate_operand" "")))]
4728   "TARGET_80387
4729    || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4730        && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)"
4731 {
4732   if (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4733         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4734       && !X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode))
4735     {
4736       rtx reg = gen_reg_rtx (XFmode);
4737       rtx (*insn)(rtx, rtx);
4738
4739       emit_insn (gen_float<SWI48x:mode>xf2 (reg, operands[1]));
4740
4741       if (<X87MODEF:MODE>mode == SFmode)
4742         insn = gen_truncxfsf2;
4743       else if (<X87MODEF:MODE>mode == DFmode)
4744         insn = gen_truncxfdf2;
4745       else
4746         gcc_unreachable ();
4747
4748       emit_insn (insn (operands[0], reg));
4749       DONE;
4750     }
4751 })
4752
4753 ;; Pre-reload splitter to add memory clobber to the pattern.
4754 (define_insn_and_split "*float<SWI48x:mode><X87MODEF:mode>2_1"
4755   [(set (match_operand:X87MODEF 0 "register_operand" "")
4756         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))]
4757   "((TARGET_80387
4758      && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
4759      && (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4760            && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4761          || TARGET_MIX_SSE_I387))
4762     || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4763         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
4764         && ((<SWI48x:MODE>mode == SImode
4765              && TARGET_SSE2 && TARGET_USE_VECTOR_CONVERTS
4766              && optimize_function_for_speed_p (cfun)
4767              && flag_trapping_math)
4768             || !(TARGET_INTER_UNIT_CONVERSIONS
4769                  || optimize_function_for_size_p (cfun)))))
4770    && can_create_pseudo_p ()"
4771   "#"
4772   "&& 1"
4773   [(parallel [(set (match_dup 0) (float:X87MODEF (match_dup 1)))
4774               (clobber (match_dup 2))])]
4775 {
4776   operands[2] = assign_386_stack_local (<SWI48x:MODE>mode, SLOT_TEMP);
4777
4778   /* Avoid store forwarding (partial memory) stall penalty
4779      by passing DImode value through XMM registers.  */
4780   if (<SWI48x:MODE>mode == DImode && !TARGET_64BIT
4781       && TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
4782       && optimize_function_for_speed_p (cfun))
4783     {
4784       emit_insn (gen_floatdi<X87MODEF:mode>2_i387_with_xmm (operands[0],
4785                                                             operands[1],
4786                                                             operands[2]));
4787       DONE;
4788     }
4789 })
4790
4791 (define_insn "*floatsi<mode>2_vector_mixed_with_temp"
4792   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x,x")
4793         (float:MODEF
4794           (match_operand:SI 1 "nonimmediate_operand" "m,?r,r,m,!x")))
4795    (clobber (match_operand:SI 2 "memory_operand" "=X,m,m,X,m"))]
4796   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4797    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4798   "#"
4799   [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
4800    (set_attr "mode" "<MODE>,<MODE>,<MODE>,<MODE>,<ssevecmode>")
4801    (set_attr "unit" "*,i387,*,*,*")
4802    (set_attr "athlon_decode" "*,*,double,direct,double")
4803    (set_attr "amdfam10_decode" "*,*,vector,double,double")
4804    (set_attr "bdver1_decode" "*,*,double,direct,double")
4805    (set_attr "fp_int_src" "true")])
4806
4807 (define_insn "*floatsi<mode>2_vector_mixed"
4808   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4809         (float:MODEF (match_operand:SI 1 "memory_operand" "m,m")))]
4810   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4811    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4812   "@
4813    fild%Z1\t%1
4814    #"
4815   [(set_attr "type" "fmov,sseicvt")
4816    (set_attr "mode" "<MODE>,<ssevecmode>")
4817    (set_attr "unit" "i387,*")
4818    (set_attr "athlon_decode" "*,direct")
4819    (set_attr "amdfam10_decode" "*,double")
4820    (set_attr "bdver1_decode" "*,direct")
4821    (set_attr "fp_int_src" "true")])
4822
4823 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_with_temp"
4824   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
4825         (float:MODEF
4826           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r,r,m")))
4827    (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m,m,X"))]
4828   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4829    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387"
4830   "#"
4831   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4832    (set_attr "mode" "<MODEF:MODE>")
4833    (set_attr "unit" "*,i387,*,*")
4834    (set_attr "athlon_decode" "*,*,double,direct")
4835    (set_attr "amdfam10_decode" "*,*,vector,double")
4836    (set_attr "bdver1_decode" "*,*,double,direct")
4837    (set_attr "fp_int_src" "true")])
4838
4839 (define_split
4840   [(set (match_operand:MODEF 0 "register_operand" "")
4841         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4842    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4843   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4844    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4845    && TARGET_INTER_UNIT_CONVERSIONS
4846    && reload_completed
4847    && (SSE_REG_P (operands[0])
4848        || (GET_CODE (operands[0]) == SUBREG
4849            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4850   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
4851
4852 (define_split
4853   [(set (match_operand:MODEF 0 "register_operand" "")
4854         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4855    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4856   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4857    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4858    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
4859    && reload_completed
4860    && (SSE_REG_P (operands[0])
4861        || (GET_CODE (operands[0]) == SUBREG
4862            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4863   [(set (match_dup 2) (match_dup 1))
4864    (set (match_dup 0) (float:MODEF (match_dup 2)))])
4865
4866 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_interunit"
4867   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
4868         (float:MODEF
4869           (match_operand:SWI48x 1 "nonimmediate_operand" "m,r,m")))]
4870   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4871    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4872    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4873   "@
4874    fild%Z1\t%1
4875    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}
4876    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4877   [(set_attr "type" "fmov,sseicvt,sseicvt")
4878    (set_attr "prefix" "orig,maybe_vex,maybe_vex")
4879    (set_attr "mode" "<MODEF:MODE>")
4880    (set (attr "prefix_rex")
4881      (if_then_else
4882        (and (eq_attr "prefix" "maybe_vex")
4883             (match_test "<SWI48x:MODE>mode == DImode"))
4884        (const_string "1")
4885        (const_string "*")))
4886    (set_attr "unit" "i387,*,*")
4887    (set_attr "athlon_decode" "*,double,direct")
4888    (set_attr "amdfam10_decode" "*,vector,double")
4889    (set_attr "bdver1_decode" "*,double,direct")
4890    (set_attr "fp_int_src" "true")])
4891
4892 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_nointerunit"
4893   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4894         (float:MODEF
4895           (match_operand:SWI48x 1 "memory_operand" "m,m")))]
4896   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4897    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4898    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4899   "@
4900    fild%Z1\t%1
4901    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4902   [(set_attr "type" "fmov,sseicvt")
4903    (set_attr "prefix" "orig,maybe_vex")
4904    (set_attr "mode" "<MODEF:MODE>")
4905    (set (attr "prefix_rex")
4906      (if_then_else
4907        (and (eq_attr "prefix" "maybe_vex")
4908             (match_test "<SWI48x:MODE>mode == DImode"))
4909        (const_string "1")
4910        (const_string "*")))
4911    (set_attr "athlon_decode" "*,direct")
4912    (set_attr "amdfam10_decode" "*,double")
4913    (set_attr "bdver1_decode" "*,direct")
4914    (set_attr "fp_int_src" "true")])
4915
4916 (define_insn "*floatsi<mode>2_vector_sse_with_temp"
4917   [(set (match_operand:MODEF 0 "register_operand" "=x,x,x")
4918         (float:MODEF
4919           (match_operand:SI 1 "nonimmediate_operand" "r,m,!x")))
4920    (clobber (match_operand:SI 2 "memory_operand" "=m,X,m"))]
4921   "TARGET_SSE2 && TARGET_SSE_MATH
4922    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4923   "#"
4924   [(set_attr "type" "sseicvt")
4925    (set_attr "mode" "<MODE>,<MODE>,<ssevecmode>")
4926    (set_attr "athlon_decode" "double,direct,double")
4927    (set_attr "amdfam10_decode" "vector,double,double")
4928    (set_attr "bdver1_decode" "double,direct,double")
4929    (set_attr "fp_int_src" "true")])
4930
4931 (define_insn "*floatsi<mode>2_vector_sse"
4932   [(set (match_operand:MODEF 0 "register_operand" "=x")
4933         (float:MODEF (match_operand:SI 1 "memory_operand" "m")))]
4934   "TARGET_SSE2 && TARGET_SSE_MATH
4935    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4936   "#"
4937   [(set_attr "type" "sseicvt")
4938    (set_attr "mode" "<MODE>")
4939    (set_attr "athlon_decode" "direct")
4940    (set_attr "amdfam10_decode" "double")
4941    (set_attr "bdver1_decode" "direct")
4942    (set_attr "fp_int_src" "true")])
4943
4944 (define_split
4945   [(set (match_operand:MODEF 0 "register_operand" "")
4946         (float:MODEF (match_operand:SI 1 "register_operand" "")))
4947    (clobber (match_operand:SI 2 "memory_operand" ""))]
4948   "TARGET_SSE2 && TARGET_SSE_MATH
4949    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
4950    && reload_completed
4951    && (SSE_REG_P (operands[0])
4952        || (GET_CODE (operands[0]) == SUBREG
4953            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4954   [(const_int 0)]
4955 {
4956   rtx op1 = operands[1];
4957
4958   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
4959                                      <MODE>mode, 0);
4960   if (GET_CODE (op1) == SUBREG)
4961     op1 = SUBREG_REG (op1);
4962
4963   if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
4964     {
4965       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
4966       emit_insn (gen_sse2_loadld (operands[4],
4967                                   CONST0_RTX (V4SImode), operands[1]));
4968     }
4969   /* We can ignore possible trapping value in the
4970      high part of SSE register for non-trapping math. */
4971   else if (SSE_REG_P (op1) && !flag_trapping_math)
4972     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
4973   else
4974     {
4975       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
4976       emit_move_insn (operands[2], operands[1]);
4977       emit_insn (gen_sse2_loadld (operands[4],
4978                                   CONST0_RTX (V4SImode), operands[2]));
4979     }
4980   if (<ssevecmode>mode == V4SFmode)
4981     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
4982   else
4983     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
4984   DONE;
4985 })
4986
4987 (define_split
4988   [(set (match_operand:MODEF 0 "register_operand" "")
4989         (float:MODEF (match_operand:SI 1 "memory_operand" "")))
4990    (clobber (match_operand:SI 2 "memory_operand" ""))]
4991   "TARGET_SSE2 && TARGET_SSE_MATH
4992    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
4993    && reload_completed
4994    && (SSE_REG_P (operands[0])
4995        || (GET_CODE (operands[0]) == SUBREG
4996            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4997   [(const_int 0)]
4998 {
4999   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5000                                      <MODE>mode, 0);
5001   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5002
5003   emit_insn (gen_sse2_loadld (operands[4],
5004                               CONST0_RTX (V4SImode), operands[1]));
5005   if (<ssevecmode>mode == V4SFmode)
5006     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5007   else
5008     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5009   DONE;
5010 })
5011
5012 (define_split
5013   [(set (match_operand:MODEF 0 "register_operand" "")
5014         (float:MODEF (match_operand:SI 1 "register_operand" "")))]
5015   "TARGET_SSE2 && TARGET_SSE_MATH
5016    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5017    && reload_completed
5018    && (SSE_REG_P (operands[0])
5019        || (GET_CODE (operands[0]) == SUBREG
5020            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5021   [(const_int 0)]
5022 {
5023   rtx op1 = operands[1];
5024
5025   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5026                                      <MODE>mode, 0);
5027   if (GET_CODE (op1) == SUBREG)
5028     op1 = SUBREG_REG (op1);
5029
5030   if (GENERAL_REG_P (op1))
5031     {
5032       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5033       if (TARGET_INTER_UNIT_MOVES)
5034         emit_insn (gen_sse2_loadld (operands[4],
5035                                     CONST0_RTX (V4SImode), operands[1]));
5036       else
5037         {
5038           operands[5] = ix86_force_to_memory (GET_MODE (operands[1]),
5039                                               operands[1]);
5040           emit_insn (gen_sse2_loadld (operands[4],
5041                                       CONST0_RTX (V4SImode), operands[5]));
5042           ix86_free_from_memory (GET_MODE (operands[1]));
5043         }
5044     }
5045   /* We can ignore possible trapping value in the
5046      high part of SSE register for non-trapping math. */
5047   else if (SSE_REG_P (op1) && !flag_trapping_math)
5048     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5049   else
5050     gcc_unreachable ();
5051   if (<ssevecmode>mode == V4SFmode)
5052     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5053   else
5054     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5055   DONE;
5056 })
5057
5058 (define_split
5059   [(set (match_operand:MODEF 0 "register_operand" "")
5060         (float:MODEF (match_operand:SI 1 "memory_operand" "")))]
5061   "TARGET_SSE2 && TARGET_SSE_MATH
5062    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5063    && reload_completed
5064    && (SSE_REG_P (operands[0])
5065        || (GET_CODE (operands[0]) == SUBREG
5066            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5067   [(const_int 0)]
5068 {
5069   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5070                                      <MODE>mode, 0);
5071   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5072
5073   emit_insn (gen_sse2_loadld (operands[4],
5074                               CONST0_RTX (V4SImode), operands[1]));
5075   if (<ssevecmode>mode == V4SFmode)
5076     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5077   else
5078     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5079   DONE;
5080 })
5081
5082 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_with_temp"
5083   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5084         (float:MODEF
5085           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))
5086   (clobber (match_operand:SWI48x 2 "memory_operand" "=m,X"))]
5087   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5088    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH"
5089   "#"
5090   [(set_attr "type" "sseicvt")
5091    (set_attr "mode" "<MODEF:MODE>")
5092    (set_attr "athlon_decode" "double,direct")
5093    (set_attr "amdfam10_decode" "vector,double")
5094    (set_attr "bdver1_decode" "double,direct")
5095    (set_attr "fp_int_src" "true")])
5096
5097 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_interunit"
5098   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5099         (float:MODEF
5100           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))]
5101   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5102    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5103    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5104   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5105   [(set_attr "type" "sseicvt")
5106    (set_attr "prefix" "maybe_vex")
5107    (set_attr "mode" "<MODEF:MODE>")
5108    (set (attr "prefix_rex")
5109      (if_then_else
5110        (and (eq_attr "prefix" "maybe_vex")
5111             (match_test "<SWI48x:MODE>mode == DImode"))
5112        (const_string "1")
5113        (const_string "*")))
5114    (set_attr "athlon_decode" "double,direct")
5115    (set_attr "amdfam10_decode" "vector,double")
5116    (set_attr "bdver1_decode" "double,direct")
5117    (set_attr "fp_int_src" "true")])
5118
5119 (define_split
5120   [(set (match_operand:MODEF 0 "register_operand" "")
5121         (float:MODEF (match_operand:SWI48x 1 "nonimmediate_operand" "")))
5122    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5123   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5124    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5125    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5126    && reload_completed
5127    && (SSE_REG_P (operands[0])
5128        || (GET_CODE (operands[0]) == SUBREG
5129            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5130   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5131
5132 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_nointerunit"
5133   [(set (match_operand:MODEF 0 "register_operand" "=x")
5134         (float:MODEF
5135           (match_operand:SWI48x 1 "memory_operand" "m")))]
5136   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5137    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5138    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5139   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5140   [(set_attr "type" "sseicvt")
5141    (set_attr "prefix" "maybe_vex")
5142    (set_attr "mode" "<MODEF:MODE>")
5143    (set (attr "prefix_rex")
5144      (if_then_else
5145        (and (eq_attr "prefix" "maybe_vex")
5146             (match_test "<SWI48x:MODE>mode == DImode"))
5147        (const_string "1")
5148        (const_string "*")))
5149    (set_attr "athlon_decode" "direct")
5150    (set_attr "amdfam10_decode" "double")
5151    (set_attr "bdver1_decode" "direct")
5152    (set_attr "fp_int_src" "true")])
5153
5154 (define_split
5155   [(set (match_operand:MODEF 0 "register_operand" "")
5156         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
5157    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5158   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5159    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5160    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5161    && reload_completed
5162    && (SSE_REG_P (operands[0])
5163        || (GET_CODE (operands[0]) == SUBREG
5164            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5165   [(set (match_dup 2) (match_dup 1))
5166    (set (match_dup 0) (float:MODEF (match_dup 2)))])
5167
5168 (define_split
5169   [(set (match_operand:MODEF 0 "register_operand" "")
5170         (float:MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5171    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5172   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5173    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5174    && reload_completed
5175    && (SSE_REG_P (operands[0])
5176        || (GET_CODE (operands[0]) == SUBREG
5177            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5178   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5179
5180 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387_with_temp"
5181   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5182         (float:X87MODEF
5183           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r")))
5184   (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m"))]
5185   "TARGET_80387
5186    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5187   "@
5188    fild%Z1\t%1
5189    #"
5190   [(set_attr "type" "fmov,multi")
5191    (set_attr "mode" "<X87MODEF:MODE>")
5192    (set_attr "unit" "*,i387")
5193    (set_attr "fp_int_src" "true")])
5194
5195 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387"
5196   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5197         (float:X87MODEF
5198           (match_operand:SWI48x 1 "memory_operand" "m")))]
5199   "TARGET_80387
5200    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5201   "fild%Z1\t%1"
5202   [(set_attr "type" "fmov")
5203    (set_attr "mode" "<X87MODEF:MODE>")
5204    (set_attr "fp_int_src" "true")])
5205
5206 (define_split
5207   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5208         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))
5209    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5210   "TARGET_80387
5211    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5212    && reload_completed"
5213   [(set (match_dup 2) (match_dup 1))
5214    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
5215
5216 (define_split
5217   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5218         (float:X87MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5219    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5220   "TARGET_80387
5221    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5222    && reload_completed"
5223   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5224
5225 ;; Avoid store forwarding (partial memory) stall penalty
5226 ;; by passing DImode value through XMM registers.  */
5227
5228 (define_insn "floatdi<X87MODEF:mode>2_i387_with_xmm"
5229   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5230         (float:X87MODEF
5231           (match_operand:DI 1 "nonimmediate_operand" "m,?r")))
5232    (clobber (match_scratch:V4SI 3 "=X,x"))
5233    (clobber (match_scratch:V4SI 4 "=X,x"))
5234    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))]
5235   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5236    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5237    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)"
5238   "#"
5239   [(set_attr "type" "multi")
5240    (set_attr "mode" "<X87MODEF:MODE>")
5241    (set_attr "unit" "i387")
5242    (set_attr "fp_int_src" "true")])
5243
5244 (define_split
5245   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5246         (float:X87MODEF (match_operand:DI 1 "register_operand" "")))
5247    (clobber (match_scratch:V4SI 3 ""))
5248    (clobber (match_scratch:V4SI 4 ""))
5249    (clobber (match_operand:DI 2 "memory_operand" ""))]
5250   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5251    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5252    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5253    && reload_completed"
5254   [(set (match_dup 2) (match_dup 3))
5255    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5256 {
5257   /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
5258      Assemble the 64-bit DImode value in an xmm register.  */
5259   emit_insn (gen_sse2_loadld (operands[3], CONST0_RTX (V4SImode),
5260                               gen_rtx_SUBREG (SImode, operands[1], 0)));
5261   emit_insn (gen_sse2_loadld (operands[4], CONST0_RTX (V4SImode),
5262                               gen_rtx_SUBREG (SImode, operands[1], 4)));
5263   emit_insn (gen_vec_interleave_lowv4si (operands[3], operands[3],
5264                                          operands[4]));
5265
5266   operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
5267 })
5268
5269 (define_split
5270   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5271         (float:X87MODEF (match_operand:DI 1 "memory_operand" "")))
5272    (clobber (match_scratch:V4SI 3 ""))
5273    (clobber (match_scratch:V4SI 4 ""))
5274    (clobber (match_operand:DI 2 "memory_operand" ""))]
5275   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5276    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5277    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5278    && reload_completed"
5279   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5280
5281 ;; Avoid store forwarding (partial memory) stall penalty by extending
5282 ;; SImode value to DImode through XMM register instead of pushing two
5283 ;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES
5284 ;; targets benefit from this optimization. Also note that fild
5285 ;; loads from memory only.
5286
5287 (define_insn "*floatunssi<mode>2_1"
5288   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5289         (unsigned_float:X87MODEF
5290           (match_operand:SI 1 "nonimmediate_operand" "x,m")))
5291    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
5292    (clobber (match_scratch:SI 3 "=X,x"))]
5293   "!TARGET_64BIT
5294    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5295    && TARGET_SSE"
5296   "#"
5297   [(set_attr "type" "multi")
5298    (set_attr "mode" "<MODE>")])
5299
5300 (define_split
5301   [(set (match_operand:X87MODEF 0 "register_operand" "")
5302         (unsigned_float:X87MODEF
5303           (match_operand:SI 1 "register_operand" "")))
5304    (clobber (match_operand:DI 2 "memory_operand" ""))
5305    (clobber (match_scratch:SI 3 ""))]
5306   "!TARGET_64BIT
5307    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5308    && TARGET_SSE
5309    && reload_completed"
5310   [(set (match_dup 2) (match_dup 1))
5311    (set (match_dup 0)
5312         (float:X87MODEF (match_dup 2)))]
5313   "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);")
5314
5315 (define_split
5316   [(set (match_operand:X87MODEF 0 "register_operand" "")
5317         (unsigned_float:X87MODEF
5318           (match_operand:SI 1 "memory_operand" "")))
5319    (clobber (match_operand:DI 2 "memory_operand" ""))
5320    (clobber (match_scratch:SI 3 ""))]
5321   "!TARGET_64BIT
5322    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5323    && TARGET_SSE
5324    && reload_completed"
5325   [(set (match_dup 2) (match_dup 3))
5326    (set (match_dup 0)
5327         (float:X87MODEF (match_dup 2)))]
5328 {
5329   emit_move_insn (operands[3], operands[1]);
5330   operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0);
5331 })
5332
5333 (define_expand "floatunssi<mode>2"
5334   [(parallel
5335      [(set (match_operand:X87MODEF 0 "register_operand" "")
5336            (unsigned_float:X87MODEF
5337              (match_operand:SI 1 "nonimmediate_operand" "")))
5338       (clobber (match_dup 2))
5339       (clobber (match_scratch:SI 3 ""))])]
5340   "!TARGET_64BIT
5341    && ((TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5342         && TARGET_SSE)
5343        || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
5344 {
5345   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5346     {
5347       ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5348       DONE;
5349     }
5350   else
5351     {
5352       enum ix86_stack_slot slot = (virtuals_instantiated
5353                                    ? SLOT_TEMP
5354                                    : SLOT_VIRTUAL);
5355       operands[2] = assign_386_stack_local (DImode, slot);
5356     }
5357 })
5358
5359 (define_expand "floatunsdisf2"
5360   [(use (match_operand:SF 0 "register_operand" ""))
5361    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5362   "TARGET_64BIT && TARGET_SSE_MATH"
5363   "x86_emit_floatuns (operands); DONE;")
5364
5365 (define_expand "floatunsdidf2"
5366   [(use (match_operand:DF 0 "register_operand" ""))
5367    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5368   "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5369    && TARGET_SSE2 && TARGET_SSE_MATH"
5370 {
5371   if (TARGET_64BIT)
5372     x86_emit_floatuns (operands);
5373   else
5374     ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5375   DONE;
5376 })
5377 \f
5378 ;; Load effective address instructions
5379
5380 (define_insn_and_split "*lea<mode>"
5381   [(set (match_operand:SWI48 0 "register_operand" "=r")
5382         (match_operand:SWI48 1 "lea_address_operand" "p"))]
5383   ""
5384 {
5385   rtx addr = operands[1];
5386
5387   if (GET_CODE (addr) == SUBREG)
5388     {
5389       gcc_assert (TARGET_64BIT);
5390       gcc_assert (<MODE>mode == SImode);
5391       gcc_assert (GET_MODE (SUBREG_REG (addr)) == DImode);
5392       return "lea{l}\t{%E1, %0|%0, %E1}";
5393     }
5394   else if (GET_CODE (addr) == ZERO_EXTEND
5395            || GET_CODE (addr) == AND)
5396     {
5397       gcc_assert (TARGET_64BIT);
5398       gcc_assert (<MODE>mode == DImode);
5399       return "lea{l}\t{%E1, %k0|%k0, %E1}";
5400     }
5401   else 
5402     return "lea{<imodesuffix>}\t{%E1, %0|%0, %E1}";
5403 }
5404   "reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
5405   [(const_int 0)]
5406 {
5407   ix86_split_lea_for_addr (operands, <MODE>mode);
5408   DONE;
5409 }
5410   [(set_attr "type" "lea")
5411    (set_attr "mode" "<MODE>")])
5412 \f
5413 ;; Add instructions
5414
5415 (define_expand "add<mode>3"
5416   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
5417         (plus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
5418                     (match_operand:SDWIM 2 "<general_operand>" "")))]
5419   ""
5420   "ix86_expand_binary_operator (PLUS, <MODE>mode, operands); DONE;")
5421
5422 (define_insn_and_split "*add<dwi>3_doubleword"
5423   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
5424         (plus:<DWI>
5425           (match_operand:<DWI> 1 "nonimmediate_operand" "%0,0")
5426           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
5427    (clobber (reg:CC FLAGS_REG))]
5428   "ix86_binary_operator_ok (PLUS, <DWI>mode, operands)"
5429   "#"
5430   "reload_completed"
5431   [(parallel [(set (reg:CC FLAGS_REG)
5432                    (unspec:CC [(match_dup 1) (match_dup 2)]
5433                               UNSPEC_ADD_CARRY))
5434               (set (match_dup 0)
5435                    (plus:DWIH (match_dup 1) (match_dup 2)))])
5436    (parallel [(set (match_dup 3)
5437                    (plus:DWIH
5438                      (match_dup 4)
5439                      (plus:DWIH
5440                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
5441                        (match_dup 5))))
5442               (clobber (reg:CC FLAGS_REG))])]
5443   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
5444
5445 (define_insn "*add<mode>3_cc"
5446   [(set (reg:CC FLAGS_REG)
5447         (unspec:CC
5448           [(match_operand:SWI48 1 "nonimmediate_operand" "%0,0")
5449            (match_operand:SWI48 2 "<general_operand>" "r<i>,rm")]
5450           UNSPEC_ADD_CARRY))
5451    (set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
5452         (plus:SWI48 (match_dup 1) (match_dup 2)))]
5453   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5454   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
5455   [(set_attr "type" "alu")
5456    (set_attr "mode" "<MODE>")])
5457
5458 (define_insn "addqi3_cc"
5459   [(set (reg:CC FLAGS_REG)
5460         (unspec:CC
5461           [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5462            (match_operand:QI 2 "general_operand" "qn,qm")]
5463           UNSPEC_ADD_CARRY))
5464    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5465         (plus:QI (match_dup 1) (match_dup 2)))]
5466   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5467   "add{b}\t{%2, %0|%0, %2}"
5468   [(set_attr "type" "alu")
5469    (set_attr "mode" "QI")])
5470
5471 (define_insn "*add<mode>_1"
5472   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,rm,r,r")
5473         (plus:SWI48
5474           (match_operand:SWI48 1 "nonimmediate_operand" "%0,0,r,r")
5475           (match_operand:SWI48 2 "x86_64_general_operand" "rme,re,0,le")))
5476    (clobber (reg:CC FLAGS_REG))]
5477   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5478 {
5479   switch (get_attr_type (insn))
5480     {
5481     case TYPE_LEA:
5482       return "#";
5483
5484     case TYPE_INCDEC:
5485       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5486       if (operands[2] == const1_rtx)
5487         return "inc{<imodesuffix>}\t%0";
5488       else
5489         {
5490           gcc_assert (operands[2] == constm1_rtx);
5491           return "dec{<imodesuffix>}\t%0";
5492         }
5493
5494     default:
5495       /* For most processors, ADD is faster than LEA.  This alternative
5496          was added to use ADD as much as possible.  */
5497       if (which_alternative == 2)
5498         {
5499           rtx tmp;
5500           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5501         }
5502         
5503       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5504       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5505         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5506
5507       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5508     }
5509 }
5510   [(set (attr "type")
5511      (cond [(eq_attr "alternative" "3")
5512               (const_string "lea")
5513             (match_operand:SWI48 2 "incdec_operand" "")
5514               (const_string "incdec")
5515            ]
5516            (const_string "alu")))
5517    (set (attr "length_immediate")
5518       (if_then_else
5519         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5520         (const_string "1")
5521         (const_string "*")))
5522    (set_attr "mode" "<MODE>")])
5523
5524 ;; It may seem that nonimmediate operand is proper one for operand 1.
5525 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5526 ;; we take care in ix86_binary_operator_ok to not allow two memory
5527 ;; operands so proper swapping will be done in reload.  This allow
5528 ;; patterns constructed from addsi_1 to match.
5529
5530 (define_insn "addsi_1_zext"
5531   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
5532         (zero_extend:DI
5533           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r,r")
5534                    (match_operand:SI 2 "x86_64_general_operand" "rme,0,le"))))
5535    (clobber (reg:CC FLAGS_REG))]
5536   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5537 {
5538   switch (get_attr_type (insn))
5539     {
5540     case TYPE_LEA:
5541       return "#";
5542
5543     case TYPE_INCDEC:
5544       if (operands[2] == const1_rtx)
5545         return "inc{l}\t%k0";
5546       else
5547         {
5548           gcc_assert (operands[2] == constm1_rtx);
5549           return "dec{l}\t%k0";
5550         }
5551
5552     default:
5553       /* For most processors, ADD is faster than LEA.  This alternative
5554          was added to use ADD as much as possible.  */
5555       if (which_alternative == 1)
5556         {
5557           rtx tmp;
5558           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5559         }
5560
5561       if (x86_maybe_negate_const_int (&operands[2], SImode))
5562         return "sub{l}\t{%2, %k0|%k0, %2}";
5563
5564       return "add{l}\t{%2, %k0|%k0, %2}";
5565     }
5566 }
5567   [(set (attr "type")
5568      (cond [(eq_attr "alternative" "2")
5569               (const_string "lea")
5570             (match_operand:SI 2 "incdec_operand" "")
5571               (const_string "incdec")
5572            ]
5573            (const_string "alu")))
5574    (set (attr "length_immediate")
5575       (if_then_else
5576         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5577         (const_string "1")
5578         (const_string "*")))
5579    (set_attr "mode" "SI")])
5580
5581 (define_insn "*addhi_1"
5582   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r,Yp")
5583         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r,Yp")
5584                  (match_operand:HI 2 "general_operand" "rn,rm,0,ln")))
5585    (clobber (reg:CC FLAGS_REG))]
5586   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5587 {
5588   switch (get_attr_type (insn))
5589     {
5590     case TYPE_LEA:
5591       return "#";
5592
5593     case TYPE_INCDEC:
5594       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5595       if (operands[2] == const1_rtx)
5596         return "inc{w}\t%0";
5597       else
5598         {
5599           gcc_assert (operands[2] == constm1_rtx);
5600           return "dec{w}\t%0";
5601         }
5602
5603     default:
5604       /* For most processors, ADD is faster than LEA.  This alternative
5605          was added to use ADD as much as possible.  */
5606       if (which_alternative == 2)
5607         {
5608           rtx tmp;
5609           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5610         }
5611
5612       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5613       if (x86_maybe_negate_const_int (&operands[2], HImode))
5614         return "sub{w}\t{%2, %0|%0, %2}";
5615
5616       return "add{w}\t{%2, %0|%0, %2}";
5617     }
5618 }
5619   [(set (attr "type")
5620      (cond [(eq_attr "alternative" "3")
5621               (const_string "lea")
5622             (match_operand:HI 2 "incdec_operand" "")
5623               (const_string "incdec")
5624            ]
5625            (const_string "alu")))
5626    (set (attr "length_immediate")
5627       (if_then_else
5628         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5629         (const_string "1")
5630         (const_string "*")))
5631    (set_attr "mode" "HI,HI,HI,SI")])
5632
5633 ;; %%% Potential partial reg stall on alternatives 3 and 4.  What to do?
5634 (define_insn "*addqi_1"
5635   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,q,r,r,Yp")
5636         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,q,0,r,Yp")
5637                  (match_operand:QI 2 "general_operand" "qn,qm,0,rn,0,ln")))
5638    (clobber (reg:CC FLAGS_REG))]
5639   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5640 {
5641   bool widen = (which_alternative == 3 || which_alternative == 4);
5642
5643   switch (get_attr_type (insn))
5644     {
5645     case TYPE_LEA:
5646       return "#";
5647
5648     case TYPE_INCDEC:
5649       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5650       if (operands[2] == const1_rtx)
5651         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
5652       else
5653         {
5654           gcc_assert (operands[2] == constm1_rtx);
5655           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
5656         }
5657
5658     default:
5659       /* For most processors, ADD is faster than LEA.  These alternatives
5660          were added to use ADD as much as possible.  */
5661       if (which_alternative == 2 || which_alternative == 4)
5662         {
5663           rtx tmp;
5664           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5665         }
5666
5667       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5668       if (x86_maybe_negate_const_int (&operands[2], QImode))
5669         {
5670           if (widen)
5671             return "sub{l}\t{%2, %k0|%k0, %2}";
5672           else
5673             return "sub{b}\t{%2, %0|%0, %2}";
5674         }
5675       if (widen)
5676         return "add{l}\t{%k2, %k0|%k0, %k2}";
5677       else
5678         return "add{b}\t{%2, %0|%0, %2}";
5679     }
5680 }
5681   [(set (attr "type")
5682      (cond [(eq_attr "alternative" "5")
5683               (const_string "lea")
5684             (match_operand:QI 2 "incdec_operand" "")
5685               (const_string "incdec")
5686            ]
5687            (const_string "alu")))
5688    (set (attr "length_immediate")
5689       (if_then_else
5690         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5691         (const_string "1")
5692         (const_string "*")))
5693    (set_attr "mode" "QI,QI,QI,SI,SI,SI")])
5694
5695 (define_insn "*addqi_1_slp"
5696   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
5697         (plus:QI (match_dup 0)
5698                  (match_operand:QI 1 "general_operand" "qn,qm")))
5699    (clobber (reg:CC FLAGS_REG))]
5700   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
5701    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
5702 {
5703   switch (get_attr_type (insn))
5704     {
5705     case TYPE_INCDEC:
5706       if (operands[1] == const1_rtx)
5707         return "inc{b}\t%0";
5708       else
5709         {
5710           gcc_assert (operands[1] == constm1_rtx);
5711           return "dec{b}\t%0";
5712         }
5713
5714     default:
5715       if (x86_maybe_negate_const_int (&operands[1], QImode))
5716         return "sub{b}\t{%1, %0|%0, %1}";
5717
5718       return "add{b}\t{%1, %0|%0, %1}";
5719     }
5720 }
5721   [(set (attr "type")
5722      (if_then_else (match_operand:QI 1 "incdec_operand" "")
5723         (const_string "incdec")
5724         (const_string "alu1")))
5725    (set (attr "memory")
5726      (if_then_else (match_operand 1 "memory_operand" "")
5727         (const_string "load")
5728         (const_string "none")))
5729    (set_attr "mode" "QI")])
5730
5731 ;; Split non destructive adds if we cannot use lea.
5732 (define_split
5733   [(set (match_operand:SWI48 0 "register_operand" "")
5734         (plus:SWI48 (match_operand:SWI48 1 "register_operand" "")
5735               (match_operand:SWI48 2 "nonmemory_operand" "")))
5736    (clobber (reg:CC FLAGS_REG))]
5737   "reload_completed && ix86_avoid_lea_for_add (insn, operands)"
5738   [(set (match_dup 0) (match_dup 1))
5739    (parallel [(set (match_dup 0) (plus:<MODE> (match_dup 0) (match_dup 2)))
5740               (clobber (reg:CC FLAGS_REG))])])
5741
5742 ;; Convert add to the lea pattern to avoid flags dependency.
5743 (define_split
5744   [(set (match_operand:SWI 0 "register_operand" "")
5745         (plus:SWI (match_operand:SWI 1 "register_operand" "")
5746                   (match_operand:SWI 2 "<nonmemory_operand>" "")))
5747    (clobber (reg:CC FLAGS_REG))]
5748   "reload_completed && ix86_lea_for_add_ok (insn, operands)" 
5749   [(const_int 0)]
5750 {
5751   enum machine_mode mode = <MODE>mode;
5752   rtx pat;
5753
5754   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
5755     { 
5756       mode = SImode; 
5757       operands[0] = gen_lowpart (mode, operands[0]);
5758       operands[1] = gen_lowpart (mode, operands[1]);
5759       operands[2] = gen_lowpart (mode, operands[2]);
5760     }
5761
5762   pat = gen_rtx_PLUS (mode, operands[1], operands[2]);
5763
5764   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5765   DONE;
5766 })
5767
5768 ;; Convert add to the lea pattern to avoid flags dependency.
5769 (define_split
5770   [(set (match_operand:DI 0 "register_operand" "")
5771         (zero_extend:DI
5772           (plus:SI (match_operand:SI 1 "register_operand" "")
5773                    (match_operand:SI 2 "x86_64_nonmemory_operand" ""))))
5774    (clobber (reg:CC FLAGS_REG))]
5775   "TARGET_64BIT && reload_completed && ix86_lea_for_add_ok (insn, operands)"
5776   [(set (match_dup 0)
5777         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))])
5778
5779 (define_insn "*add<mode>_2"
5780   [(set (reg FLAGS_REG)
5781         (compare
5782           (plus:SWI
5783             (match_operand:SWI 1 "nonimmediate_operand" "%0,0,<r>")
5784             (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>,0"))
5785           (const_int 0)))
5786    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m,<r>")
5787         (plus:SWI (match_dup 1) (match_dup 2)))]
5788   "ix86_match_ccmode (insn, CCGOCmode)
5789    && ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5790 {
5791   switch (get_attr_type (insn))
5792     {
5793     case TYPE_INCDEC:
5794       if (operands[2] == const1_rtx)
5795         return "inc{<imodesuffix>}\t%0";
5796       else
5797         {
5798           gcc_assert (operands[2] == constm1_rtx);
5799           return "dec{<imodesuffix>}\t%0";
5800         }
5801
5802     default:
5803       if (which_alternative == 2)
5804         {
5805           rtx tmp;
5806           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5807         }
5808         
5809       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5810       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5811         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5812
5813       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5814     }
5815 }
5816   [(set (attr "type")
5817      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5818         (const_string "incdec")
5819         (const_string "alu")))
5820    (set (attr "length_immediate")
5821       (if_then_else
5822         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5823         (const_string "1")
5824         (const_string "*")))
5825    (set_attr "mode" "<MODE>")])
5826
5827 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5828 (define_insn "*addsi_2_zext"
5829   [(set (reg FLAGS_REG)
5830         (compare
5831           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5832                    (match_operand:SI 2 "x86_64_general_operand" "rme,0"))
5833           (const_int 0)))
5834    (set (match_operand:DI 0 "register_operand" "=r,r")
5835         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5836   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5837    && ix86_binary_operator_ok (PLUS, SImode, operands)"
5838 {
5839   switch (get_attr_type (insn))
5840     {
5841     case TYPE_INCDEC:
5842       if (operands[2] == const1_rtx)
5843         return "inc{l}\t%k0";
5844       else
5845         {
5846           gcc_assert (operands[2] == constm1_rtx);
5847           return "dec{l}\t%k0";
5848         }
5849
5850     default:
5851       if (which_alternative == 1)
5852         {
5853           rtx tmp;
5854           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5855         }
5856
5857       if (x86_maybe_negate_const_int (&operands[2], SImode))
5858         return "sub{l}\t{%2, %k0|%k0, %2}";
5859
5860       return "add{l}\t{%2, %k0|%k0, %2}";
5861     }
5862 }
5863   [(set (attr "type")
5864      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5865         (const_string "incdec")
5866         (const_string "alu")))
5867    (set (attr "length_immediate")
5868       (if_then_else
5869         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5870         (const_string "1")
5871         (const_string "*")))
5872    (set_attr "mode" "SI")])
5873
5874 (define_insn "*add<mode>_3"
5875   [(set (reg FLAGS_REG)
5876         (compare
5877           (neg:SWI (match_operand:SWI 2 "<general_operand>" "<g>,0"))
5878           (match_operand:SWI 1 "nonimmediate_operand" "%0,<r>")))
5879    (clobber (match_scratch:SWI 0 "=<r>,<r>"))]
5880   "ix86_match_ccmode (insn, CCZmode)
5881    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
5882 {
5883   switch (get_attr_type (insn))
5884     {
5885     case TYPE_INCDEC:
5886       if (operands[2] == const1_rtx)
5887         return "inc{<imodesuffix>}\t%0";
5888       else
5889         {
5890           gcc_assert (operands[2] == constm1_rtx);
5891           return "dec{<imodesuffix>}\t%0";
5892         }
5893
5894     default:
5895       if (which_alternative == 1)
5896         {
5897           rtx tmp;
5898           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5899         }
5900
5901       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5902       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5903         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5904
5905       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5906     }
5907 }
5908   [(set (attr "type")
5909      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5910         (const_string "incdec")
5911         (const_string "alu")))
5912    (set (attr "length_immediate")
5913       (if_then_else
5914         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5915         (const_string "1")
5916         (const_string "*")))
5917    (set_attr "mode" "<MODE>")])
5918
5919 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5920 (define_insn "*addsi_3_zext"
5921   [(set (reg FLAGS_REG)
5922         (compare
5923           (neg:SI (match_operand:SI 2 "x86_64_general_operand" "rme,0"))
5924           (match_operand:SI 1 "nonimmediate_operand" "%0,r")))
5925    (set (match_operand:DI 0 "register_operand" "=r,r")
5926         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5927   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5928    && ix86_binary_operator_ok (PLUS, SImode, operands)"
5929 {
5930   switch (get_attr_type (insn))
5931     {
5932     case TYPE_INCDEC:
5933       if (operands[2] == const1_rtx)
5934         return "inc{l}\t%k0";
5935       else
5936         {
5937           gcc_assert (operands[2] == constm1_rtx);
5938           return "dec{l}\t%k0";
5939         }
5940
5941     default:
5942       if (which_alternative == 1)
5943         {
5944           rtx tmp;
5945           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5946         }
5947
5948       if (x86_maybe_negate_const_int (&operands[2], SImode))
5949         return "sub{l}\t{%2, %k0|%k0, %2}";
5950
5951       return "add{l}\t{%2, %k0|%k0, %2}";
5952     }
5953 }
5954   [(set (attr "type")
5955      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5956         (const_string "incdec")
5957         (const_string "alu")))
5958    (set (attr "length_immediate")
5959       (if_then_else
5960         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5961         (const_string "1")
5962         (const_string "*")))
5963    (set_attr "mode" "SI")])
5964
5965 ; For comparisons against 1, -1 and 128, we may generate better code
5966 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5967 ; is matched then.  We can't accept general immediate, because for
5968 ; case of overflows,  the result is messed up.
5969 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5970 ; only for comparisons not depending on it.
5971
5972 (define_insn "*adddi_4"
5973   [(set (reg FLAGS_REG)
5974         (compare
5975           (match_operand:DI 1 "nonimmediate_operand" "0")
5976           (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5977    (clobber (match_scratch:DI 0 "=rm"))]
5978   "TARGET_64BIT
5979    && ix86_match_ccmode (insn, CCGCmode)"
5980 {
5981   switch (get_attr_type (insn))
5982     {
5983     case TYPE_INCDEC:
5984       if (operands[2] == constm1_rtx)
5985         return "inc{q}\t%0";
5986       else
5987         {
5988           gcc_assert (operands[2] == const1_rtx);
5989           return "dec{q}\t%0";
5990         }
5991
5992     default:
5993       if (x86_maybe_negate_const_int (&operands[2], DImode))
5994         return "add{q}\t{%2, %0|%0, %2}";
5995
5996       return "sub{q}\t{%2, %0|%0, %2}";
5997     }
5998 }
5999   [(set (attr "type")
6000      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6001         (const_string "incdec")
6002         (const_string "alu")))
6003    (set (attr "length_immediate")
6004       (if_then_else
6005         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6006         (const_string "1")
6007         (const_string "*")))
6008    (set_attr "mode" "DI")])
6009
6010 ; For comparisons against 1, -1 and 128, we may generate better code
6011 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6012 ; is matched then.  We can't accept general immediate, because for
6013 ; case of overflows,  the result is messed up.
6014 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6015 ; only for comparisons not depending on it.
6016
6017 (define_insn "*add<mode>_4"
6018   [(set (reg FLAGS_REG)
6019         (compare
6020           (match_operand:SWI124 1 "nonimmediate_operand" "0")
6021           (match_operand:SWI124 2 "const_int_operand" "n")))
6022    (clobber (match_scratch:SWI124 0 "=<r>m"))]
6023   "ix86_match_ccmode (insn, CCGCmode)"
6024 {
6025   switch (get_attr_type (insn))
6026     {
6027     case TYPE_INCDEC:
6028       if (operands[2] == constm1_rtx)
6029         return "inc{<imodesuffix>}\t%0";
6030       else
6031         {
6032           gcc_assert (operands[2] == const1_rtx);
6033           return "dec{<imodesuffix>}\t%0";
6034         }
6035
6036     default:
6037       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6038         return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6039
6040       return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6041     }
6042 }
6043   [(set (attr "type")
6044      (if_then_else (match_operand:<MODE> 2 "incdec_operand" "")
6045         (const_string "incdec")
6046         (const_string "alu")))
6047    (set (attr "length_immediate")
6048       (if_then_else
6049         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6050         (const_string "1")
6051         (const_string "*")))
6052    (set_attr "mode" "<MODE>")])
6053
6054 (define_insn "*add<mode>_5"
6055   [(set (reg FLAGS_REG)
6056         (compare
6057           (plus:SWI
6058             (match_operand:SWI 1 "nonimmediate_operand" "%0,<r>")
6059             (match_operand:SWI 2 "<general_operand>" "<g>,0"))
6060           (const_int 0)))
6061    (clobber (match_scratch:SWI 0 "=<r>,<r>"))]
6062   "ix86_match_ccmode (insn, CCGOCmode)
6063    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6064 {
6065   switch (get_attr_type (insn))
6066     {
6067     case TYPE_INCDEC:
6068       if (operands[2] == const1_rtx)
6069         return "inc{<imodesuffix>}\t%0";
6070       else
6071         {
6072           gcc_assert (operands[2] == constm1_rtx);
6073           return "dec{<imodesuffix>}\t%0";
6074         }
6075
6076     default:
6077       if (which_alternative == 1)
6078         {
6079           rtx tmp;
6080           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
6081         }
6082
6083       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6084       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6085         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6086
6087       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6088     }
6089 }
6090   [(set (attr "type")
6091      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
6092         (const_string "incdec")
6093         (const_string "alu")))
6094    (set (attr "length_immediate")
6095       (if_then_else
6096         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6097         (const_string "1")
6098         (const_string "*")))
6099    (set_attr "mode" "<MODE>")])
6100
6101 (define_insn "*addqi_ext_1_rex64"
6102   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6103                          (const_int 8)
6104                          (const_int 8))
6105         (plus:SI
6106           (zero_extract:SI
6107             (match_operand 1 "ext_register_operand" "0")
6108             (const_int 8)
6109             (const_int 8))
6110           (match_operand:QI 2 "nonmemory_operand" "Qn")))
6111    (clobber (reg:CC FLAGS_REG))]
6112   "TARGET_64BIT"
6113 {
6114   switch (get_attr_type (insn))
6115     {
6116     case TYPE_INCDEC:
6117       if (operands[2] == const1_rtx)
6118         return "inc{b}\t%h0";
6119       else
6120         {
6121           gcc_assert (operands[2] == constm1_rtx);
6122           return "dec{b}\t%h0";
6123         }
6124
6125     default:
6126       return "add{b}\t{%2, %h0|%h0, %2}";
6127     }
6128 }
6129   [(set (attr "type")
6130      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6131         (const_string "incdec")
6132         (const_string "alu")))
6133    (set_attr "modrm" "1")
6134    (set_attr "mode" "QI")])
6135
6136 (define_insn "addqi_ext_1"
6137   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6138                          (const_int 8)
6139                          (const_int 8))
6140         (plus:SI
6141           (zero_extract:SI
6142             (match_operand 1 "ext_register_operand" "0")
6143             (const_int 8)
6144             (const_int 8))
6145           (match_operand:QI 2 "general_operand" "Qmn")))
6146    (clobber (reg:CC FLAGS_REG))]
6147   "!TARGET_64BIT"
6148 {
6149   switch (get_attr_type (insn))
6150     {
6151     case TYPE_INCDEC:
6152       if (operands[2] == const1_rtx)
6153         return "inc{b}\t%h0";
6154       else
6155         {
6156           gcc_assert (operands[2] == constm1_rtx);
6157           return "dec{b}\t%h0";
6158         }
6159
6160     default:
6161       return "add{b}\t{%2, %h0|%h0, %2}";
6162     }
6163 }
6164   [(set (attr "type")
6165      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6166         (const_string "incdec")
6167         (const_string "alu")))
6168    (set_attr "modrm" "1")
6169    (set_attr "mode" "QI")])
6170
6171 (define_insn "*addqi_ext_2"
6172   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6173                          (const_int 8)
6174                          (const_int 8))
6175         (plus:SI
6176           (zero_extract:SI
6177             (match_operand 1 "ext_register_operand" "%0")
6178             (const_int 8)
6179             (const_int 8))
6180           (zero_extract:SI
6181             (match_operand 2 "ext_register_operand" "Q")
6182             (const_int 8)
6183             (const_int 8))))
6184    (clobber (reg:CC FLAGS_REG))]
6185   ""
6186   "add{b}\t{%h2, %h0|%h0, %h2}"
6187   [(set_attr "type" "alu")
6188    (set_attr "mode" "QI")])
6189
6190 ;; The lea patterns for modes less than 32 bits need to be matched by
6191 ;; several insns converted to real lea by splitters.
6192
6193 (define_insn_and_split "*lea_general_1"
6194   [(set (match_operand 0 "register_operand" "=r")
6195         (plus (plus (match_operand 1 "index_register_operand" "l")
6196                     (match_operand 2 "register_operand" "r"))
6197               (match_operand 3 "immediate_operand" "i")))]
6198   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6199    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6200    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6201    && GET_MODE (operands[0]) == GET_MODE (operands[2])
6202    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6203        || GET_MODE (operands[3]) == VOIDmode)"
6204   "#"
6205   "&& reload_completed"
6206   [(const_int 0)]
6207 {
6208   enum machine_mode mode = SImode;
6209   rtx pat;
6210
6211   operands[0] = gen_lowpart (mode, operands[0]);
6212   operands[1] = gen_lowpart (mode, operands[1]);
6213   operands[2] = gen_lowpart (mode, operands[2]);
6214   operands[3] = gen_lowpart (mode, operands[3]);
6215
6216   pat = gen_rtx_PLUS (mode, gen_rtx_PLUS (mode, operands[1], operands[2]),
6217                       operands[3]);
6218
6219   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6220   DONE;
6221 }
6222   [(set_attr "type" "lea")
6223    (set_attr "mode" "SI")])
6224
6225 (define_insn_and_split "*lea_general_2"
6226   [(set (match_operand 0 "register_operand" "=r")
6227         (plus (mult (match_operand 1 "index_register_operand" "l")
6228                     (match_operand 2 "const248_operand" "n"))
6229               (match_operand 3 "nonmemory_operand" "ri")))]
6230   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6231    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6232    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6233    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6234        || GET_MODE (operands[3]) == VOIDmode)"
6235   "#"
6236   "&& reload_completed"
6237   [(const_int 0)]
6238 {
6239   enum machine_mode mode = SImode;
6240   rtx pat;
6241
6242   operands[0] = gen_lowpart (mode, operands[0]);
6243   operands[1] = gen_lowpart (mode, operands[1]);
6244   operands[3] = gen_lowpart (mode, operands[3]);
6245
6246   pat = gen_rtx_PLUS (mode, gen_rtx_MULT (mode, operands[1], operands[2]),
6247                       operands[3]);
6248
6249   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6250   DONE;
6251 }
6252   [(set_attr "type" "lea")
6253    (set_attr "mode" "SI")])
6254
6255 (define_insn_and_split "*lea_general_3"
6256   [(set (match_operand 0 "register_operand" "=r")
6257         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
6258                           (match_operand 2 "const248_operand" "n"))
6259                     (match_operand 3 "register_operand" "r"))
6260               (match_operand 4 "immediate_operand" "i")))]
6261   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6262    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6263    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6264    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
6265   "#"
6266   "&& reload_completed"
6267   [(const_int 0)]
6268 {
6269   enum machine_mode mode = SImode;
6270   rtx pat;
6271
6272   operands[0] = gen_lowpart (mode, operands[0]);
6273   operands[1] = gen_lowpart (mode, operands[1]);
6274   operands[3] = gen_lowpart (mode, operands[3]);
6275   operands[4] = gen_lowpart (mode, operands[4]);
6276
6277   pat = gen_rtx_PLUS (mode,
6278                       gen_rtx_PLUS (mode,
6279                                     gen_rtx_MULT (mode, operands[1],
6280                                                         operands[2]),
6281                                     operands[3]),
6282                       operands[4]);
6283
6284   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6285   DONE;
6286 }
6287   [(set_attr "type" "lea")
6288    (set_attr "mode" "SI")])
6289
6290 (define_insn_and_split "*lea_general_4"
6291   [(set (match_operand 0 "register_operand" "=r")
6292         (any_or (ashift
6293                   (match_operand 1 "index_register_operand" "l")
6294                   (match_operand 2 "const_int_operand" "n"))
6295                 (match_operand 3 "const_int_operand" "n")))]
6296   "(((GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6297       && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)))
6298     || GET_MODE (operands[0]) == SImode
6299     || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
6300    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6301    && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) - 1 < 3
6302    && ((unsigned HOST_WIDE_INT) INTVAL (operands[3])
6303        < ((unsigned HOST_WIDE_INT) 1 << INTVAL (operands[2])))"
6304   "#"
6305   "&& reload_completed"
6306   [(const_int 0)]
6307 {
6308   enum machine_mode mode = GET_MODE (operands[0]);
6309   rtx pat;
6310
6311   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
6312     { 
6313       mode = SImode; 
6314       operands[0] = gen_lowpart (mode, operands[0]);
6315       operands[1] = gen_lowpart (mode, operands[1]);
6316     }
6317
6318   operands[2] = GEN_INT (1 << INTVAL (operands[2]));
6319
6320   pat = plus_constant (gen_rtx_MULT (mode, operands[1], operands[2]),
6321                        INTVAL (operands[3]));
6322
6323   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6324   DONE;
6325 }
6326   [(set_attr "type" "lea")
6327    (set (attr "mode")
6328       (if_then_else (match_operand:DI 0 "" "")
6329         (const_string "DI")
6330         (const_string "SI")))])
6331 \f
6332 ;; Subtract instructions
6333
6334 (define_expand "sub<mode>3"
6335   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
6336         (minus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
6337                      (match_operand:SDWIM 2 "<general_operand>" "")))]
6338   ""
6339   "ix86_expand_binary_operator (MINUS, <MODE>mode, operands); DONE;")
6340
6341 (define_insn_and_split "*sub<dwi>3_doubleword"
6342   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
6343         (minus:<DWI>
6344           (match_operand:<DWI> 1 "nonimmediate_operand" "0,0")
6345           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
6346    (clobber (reg:CC FLAGS_REG))]
6347   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6348   "#"
6349   "reload_completed"
6350   [(parallel [(set (reg:CC FLAGS_REG)
6351                    (compare:CC (match_dup 1) (match_dup 2)))
6352               (set (match_dup 0)
6353                    (minus:DWIH (match_dup 1) (match_dup 2)))])
6354    (parallel [(set (match_dup 3)
6355                    (minus:DWIH
6356                      (match_dup 4)
6357                      (plus:DWIH
6358                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
6359                        (match_dup 5))))
6360               (clobber (reg:CC FLAGS_REG))])]
6361   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
6362
6363 (define_insn "*sub<mode>_1"
6364   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6365         (minus:SWI
6366           (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6367           (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6368    (clobber (reg:CC FLAGS_REG))]
6369   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6370   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6371   [(set_attr "type" "alu")
6372    (set_attr "mode" "<MODE>")])
6373
6374 (define_insn "*subsi_1_zext"
6375   [(set (match_operand:DI 0 "register_operand" "=r")
6376         (zero_extend:DI
6377           (minus:SI (match_operand:SI 1 "register_operand" "0")
6378                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
6379    (clobber (reg:CC FLAGS_REG))]
6380   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6381   "sub{l}\t{%2, %k0|%k0, %2}"
6382   [(set_attr "type" "alu")
6383    (set_attr "mode" "SI")])
6384
6385 (define_insn "*subqi_1_slp"
6386   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6387         (minus:QI (match_dup 0)
6388                   (match_operand:QI 1 "general_operand" "qn,qm")))
6389    (clobber (reg:CC FLAGS_REG))]
6390   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6391    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6392   "sub{b}\t{%1, %0|%0, %1}"
6393   [(set_attr "type" "alu1")
6394    (set_attr "mode" "QI")])
6395
6396 (define_insn "*sub<mode>_2"
6397   [(set (reg FLAGS_REG)
6398         (compare
6399           (minus:SWI
6400             (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6401             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6402           (const_int 0)))
6403    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6404         (minus:SWI (match_dup 1) (match_dup 2)))]
6405   "ix86_match_ccmode (insn, CCGOCmode)
6406    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6407   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6408   [(set_attr "type" "alu")
6409    (set_attr "mode" "<MODE>")])
6410
6411 (define_insn "*subsi_2_zext"
6412   [(set (reg FLAGS_REG)
6413         (compare
6414           (minus:SI (match_operand:SI 1 "register_operand" "0")
6415                     (match_operand:SI 2 "x86_64_general_operand" "rme"))
6416           (const_int 0)))
6417    (set (match_operand:DI 0 "register_operand" "=r")
6418         (zero_extend:DI
6419           (minus:SI (match_dup 1)
6420                     (match_dup 2))))]
6421   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6422    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6423   "sub{l}\t{%2, %k0|%k0, %2}"
6424   [(set_attr "type" "alu")
6425    (set_attr "mode" "SI")])
6426
6427 (define_insn "*sub<mode>_3"
6428   [(set (reg FLAGS_REG)
6429         (compare (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6430                  (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6431    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6432         (minus:SWI (match_dup 1) (match_dup 2)))]
6433   "ix86_match_ccmode (insn, CCmode)
6434    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6435   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6436   [(set_attr "type" "alu")
6437    (set_attr "mode" "<MODE>")])
6438
6439 (define_insn "*subsi_3_zext"
6440   [(set (reg FLAGS_REG)
6441         (compare (match_operand:SI 1 "register_operand" "0")
6442                  (match_operand:SI 2 "x86_64_general_operand" "rme")))
6443    (set (match_operand:DI 0 "register_operand" "=r")
6444         (zero_extend:DI
6445           (minus:SI (match_dup 1)
6446                     (match_dup 2))))]
6447   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6448    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6449   "sub{l}\t{%2, %1|%1, %2}"
6450   [(set_attr "type" "alu")
6451    (set_attr "mode" "SI")])
6452 \f
6453 ;; Add with carry and subtract with borrow
6454
6455 (define_expand "<plusminus_insn><mode>3_carry"
6456   [(parallel
6457     [(set (match_operand:SWI 0 "nonimmediate_operand" "")
6458           (plusminus:SWI
6459             (match_operand:SWI 1 "nonimmediate_operand" "")
6460             (plus:SWI (match_operator:SWI 4 "ix86_carry_flag_operator"
6461                        [(match_operand 3 "flags_reg_operand" "")
6462                         (const_int 0)])
6463                       (match_operand:SWI 2 "<general_operand>" ""))))
6464      (clobber (reg:CC FLAGS_REG))])]
6465   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)")
6466
6467 (define_insn "*<plusminus_insn><mode>3_carry"
6468   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6469         (plusminus:SWI
6470           (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6471           (plus:SWI
6472             (match_operator 3 "ix86_carry_flag_operator"
6473              [(reg FLAGS_REG) (const_int 0)])
6474             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))))
6475    (clobber (reg:CC FLAGS_REG))]
6476   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
6477   "<plusminus_carry_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6478   [(set_attr "type" "alu")
6479    (set_attr "use_carry" "1")
6480    (set_attr "pent_pair" "pu")
6481    (set_attr "mode" "<MODE>")])
6482
6483 (define_insn "*addsi3_carry_zext"
6484   [(set (match_operand:DI 0 "register_operand" "=r")
6485         (zero_extend:DI
6486           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6487                    (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6488                              [(reg FLAGS_REG) (const_int 0)])
6489                             (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6490    (clobber (reg:CC FLAGS_REG))]
6491   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6492   "adc{l}\t{%2, %k0|%k0, %2}"
6493   [(set_attr "type" "alu")
6494    (set_attr "use_carry" "1")
6495    (set_attr "pent_pair" "pu")
6496    (set_attr "mode" "SI")])
6497
6498 (define_insn "*subsi3_carry_zext"
6499   [(set (match_operand:DI 0 "register_operand" "=r")
6500         (zero_extend:DI
6501           (minus:SI (match_operand:SI 1 "register_operand" "0")
6502                     (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6503                               [(reg FLAGS_REG) (const_int 0)])
6504                              (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6505    (clobber (reg:CC FLAGS_REG))]
6506   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6507   "sbb{l}\t{%2, %k0|%k0, %2}"
6508   [(set_attr "type" "alu")
6509    (set_attr "pent_pair" "pu")
6510    (set_attr "mode" "SI")])
6511 \f
6512 ;; Overflow setting add and subtract instructions
6513
6514 (define_insn "*add<mode>3_cconly_overflow"
6515   [(set (reg:CCC FLAGS_REG)
6516         (compare:CCC
6517           (plus:SWI
6518             (match_operand:SWI 1 "nonimmediate_operand" "%0")
6519             (match_operand:SWI 2 "<general_operand>" "<g>"))
6520           (match_dup 1)))
6521    (clobber (match_scratch:SWI 0 "=<r>"))]
6522   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6523   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
6524   [(set_attr "type" "alu")
6525    (set_attr "mode" "<MODE>")])
6526
6527 (define_insn "*sub<mode>3_cconly_overflow"
6528   [(set (reg:CCC FLAGS_REG)
6529         (compare:CCC
6530           (minus:SWI
6531             (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
6532             (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
6533           (match_dup 0)))]
6534   ""
6535   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
6536   [(set_attr "type" "icmp")
6537    (set_attr "mode" "<MODE>")])
6538
6539 (define_insn "*<plusminus_insn><mode>3_cc_overflow"
6540   [(set (reg:CCC FLAGS_REG)
6541         (compare:CCC
6542             (plusminus:SWI
6543                 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6544                 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6545             (match_dup 1)))
6546    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6547         (plusminus:SWI (match_dup 1) (match_dup 2)))]
6548   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6549   "<plusminus_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6550   [(set_attr "type" "alu")
6551    (set_attr "mode" "<MODE>")])
6552
6553 (define_insn "*<plusminus_insn>si3_zext_cc_overflow"
6554   [(set (reg:CCC FLAGS_REG)
6555         (compare:CCC
6556           (plusminus:SI
6557             (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
6558             (match_operand:SI 2 "x86_64_general_operand" "rme"))
6559           (match_dup 1)))
6560    (set (match_operand:DI 0 "register_operand" "=r")
6561         (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
6562   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
6563   "<plusminus_mnemonic>{l}\t{%2, %k0|%k0, %2}"
6564   [(set_attr "type" "alu")
6565    (set_attr "mode" "SI")])
6566
6567 ;; The patterns that match these are at the end of this file.
6568
6569 (define_expand "<plusminus_insn>xf3"
6570   [(set (match_operand:XF 0 "register_operand" "")
6571         (plusminus:XF
6572           (match_operand:XF 1 "register_operand" "")
6573           (match_operand:XF 2 "register_operand" "")))]
6574   "TARGET_80387")
6575
6576 (define_expand "<plusminus_insn><mode>3"
6577   [(set (match_operand:MODEF 0 "register_operand" "")
6578         (plusminus:MODEF
6579           (match_operand:MODEF 1 "register_operand" "")
6580           (match_operand:MODEF 2 "nonimmediate_operand" "")))]
6581   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
6582     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
6583 \f
6584 ;; Multiply instructions
6585
6586 (define_expand "mul<mode>3"
6587   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
6588                    (mult:SWIM248
6589                      (match_operand:SWIM248 1 "register_operand" "")
6590                      (match_operand:SWIM248 2 "<general_operand>" "")))
6591               (clobber (reg:CC FLAGS_REG))])])
6592
6593 (define_expand "mulqi3"
6594   [(parallel [(set (match_operand:QI 0 "register_operand" "")
6595                    (mult:QI
6596                      (match_operand:QI 1 "register_operand" "")
6597                      (match_operand:QI 2 "nonimmediate_operand" "")))
6598               (clobber (reg:CC FLAGS_REG))])]
6599   "TARGET_QIMODE_MATH")
6600
6601 ;; On AMDFAM10
6602 ;; IMUL reg32/64, reg32/64, imm8        Direct
6603 ;; IMUL reg32/64, mem32/64, imm8        VectorPath
6604 ;; IMUL reg32/64, reg32/64, imm32       Direct
6605 ;; IMUL reg32/64, mem32/64, imm32       VectorPath
6606 ;; IMUL reg32/64, reg32/64              Direct
6607 ;; IMUL reg32/64, mem32/64              Direct
6608 ;;
6609 ;; On BDVER1, all above IMULs use DirectPath
6610
6611 (define_insn "*mul<mode>3_1"
6612   [(set (match_operand:SWI48 0 "register_operand" "=r,r,r")
6613         (mult:SWI48
6614           (match_operand:SWI48 1 "nonimmediate_operand" "%rm,rm,0")
6615           (match_operand:SWI48 2 "<general_operand>" "K,<i>,mr")))
6616    (clobber (reg:CC FLAGS_REG))]
6617   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6618   "@
6619    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6620    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6621    imul{<imodesuffix>}\t{%2, %0|%0, %2}"
6622   [(set_attr "type" "imul")
6623    (set_attr "prefix_0f" "0,0,1")
6624    (set (attr "athlon_decode")
6625         (cond [(eq_attr "cpu" "athlon")
6626                   (const_string "vector")
6627                (eq_attr "alternative" "1")
6628                   (const_string "vector")
6629                (and (eq_attr "alternative" "2")
6630                     (match_operand 1 "memory_operand" ""))
6631                   (const_string "vector")]
6632               (const_string "direct")))
6633    (set (attr "amdfam10_decode")
6634         (cond [(and (eq_attr "alternative" "0,1")
6635                     (match_operand 1 "memory_operand" ""))
6636                   (const_string "vector")]
6637               (const_string "direct")))
6638    (set_attr "bdver1_decode" "direct")
6639    (set_attr "mode" "<MODE>")])
6640
6641 (define_insn "*mulsi3_1_zext"
6642   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6643         (zero_extend:DI
6644           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6645                    (match_operand:SI 2 "x86_64_general_operand" "K,e,mr"))))
6646    (clobber (reg:CC FLAGS_REG))]
6647   "TARGET_64BIT
6648    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6649   "@
6650    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6651    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6652    imul{l}\t{%2, %k0|%k0, %2}"
6653   [(set_attr "type" "imul")
6654    (set_attr "prefix_0f" "0,0,1")
6655    (set (attr "athlon_decode")
6656         (cond [(eq_attr "cpu" "athlon")
6657                   (const_string "vector")
6658                (eq_attr "alternative" "1")
6659                   (const_string "vector")
6660                (and (eq_attr "alternative" "2")
6661                     (match_operand 1 "memory_operand" ""))
6662                   (const_string "vector")]
6663               (const_string "direct")))
6664    (set (attr "amdfam10_decode")
6665         (cond [(and (eq_attr "alternative" "0,1")
6666                     (match_operand 1 "memory_operand" ""))
6667                   (const_string "vector")]
6668               (const_string "direct")))
6669    (set_attr "bdver1_decode" "direct")
6670    (set_attr "mode" "SI")])
6671
6672 ;; On AMDFAM10
6673 ;; IMUL reg16, reg16, imm8      VectorPath
6674 ;; IMUL reg16, mem16, imm8      VectorPath
6675 ;; IMUL reg16, reg16, imm16     VectorPath
6676 ;; IMUL reg16, mem16, imm16     VectorPath
6677 ;; IMUL reg16, reg16            Direct
6678 ;; IMUL reg16, mem16            Direct
6679 ;;
6680 ;; On BDVER1, all HI MULs use DoublePath
6681
6682 (define_insn "*mulhi3_1"
6683   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6684         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6685                  (match_operand:HI 2 "general_operand" "K,n,mr")))
6686    (clobber (reg:CC FLAGS_REG))]
6687   "TARGET_HIMODE_MATH
6688    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6689   "@
6690    imul{w}\t{%2, %1, %0|%0, %1, %2}
6691    imul{w}\t{%2, %1, %0|%0, %1, %2}
6692    imul{w}\t{%2, %0|%0, %2}"
6693   [(set_attr "type" "imul")
6694    (set_attr "prefix_0f" "0,0,1")
6695    (set (attr "athlon_decode")
6696         (cond [(eq_attr "cpu" "athlon")
6697                   (const_string "vector")
6698                (eq_attr "alternative" "1,2")
6699                   (const_string "vector")]
6700               (const_string "direct")))
6701    (set (attr "amdfam10_decode")
6702         (cond [(eq_attr "alternative" "0,1")
6703                   (const_string "vector")]
6704               (const_string "direct")))
6705    (set_attr "bdver1_decode" "double")
6706    (set_attr "mode" "HI")])
6707
6708 ;;On AMDFAM10 and BDVER1
6709 ;; MUL reg8     Direct
6710 ;; MUL mem8     Direct
6711
6712 (define_insn "*mulqi3_1"
6713   [(set (match_operand:QI 0 "register_operand" "=a")
6714         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6715                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
6716    (clobber (reg:CC FLAGS_REG))]
6717   "TARGET_QIMODE_MATH
6718    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6719   "mul{b}\t%2"
6720   [(set_attr "type" "imul")
6721    (set_attr "length_immediate" "0")
6722    (set (attr "athlon_decode")
6723      (if_then_else (eq_attr "cpu" "athlon")
6724         (const_string "vector")
6725         (const_string "direct")))
6726    (set_attr "amdfam10_decode" "direct")
6727    (set_attr "bdver1_decode" "direct")
6728    (set_attr "mode" "QI")])
6729
6730 (define_expand "<u>mul<mode><dwi>3"
6731   [(parallel [(set (match_operand:<DWI> 0 "register_operand" "")
6732                    (mult:<DWI>
6733                      (any_extend:<DWI>
6734                        (match_operand:DWIH 1 "nonimmediate_operand" ""))
6735                      (any_extend:<DWI>
6736                        (match_operand:DWIH 2 "register_operand" ""))))
6737               (clobber (reg:CC FLAGS_REG))])])
6738
6739 (define_expand "<u>mulqihi3"
6740   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6741                    (mult:HI
6742                      (any_extend:HI
6743                        (match_operand:QI 1 "nonimmediate_operand" ""))
6744                      (any_extend:HI
6745                        (match_operand:QI 2 "register_operand" ""))))
6746               (clobber (reg:CC FLAGS_REG))])]
6747   "TARGET_QIMODE_MATH")
6748
6749 (define_insn "*bmi2_umulditi3_1"
6750   [(set (match_operand:DI 0 "register_operand" "=r")
6751         (mult:DI
6752           (match_operand:DI 2 "nonimmediate_operand" "%d")
6753           (match_operand:DI 3 "nonimmediate_operand" "rm")))
6754    (set (match_operand:DI 1 "register_operand" "=r")
6755         (truncate:DI
6756           (lshiftrt:TI
6757             (mult:TI (zero_extend:TI (match_dup 2))
6758                      (zero_extend:TI (match_dup 3)))
6759             (const_int 64))))]
6760   "TARGET_64BIT && TARGET_BMI2
6761    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6762   "mulx\t{%3, %0, %1|%1, %0, %3}"
6763   [(set_attr "type" "imulx")
6764    (set_attr "prefix" "vex")
6765    (set_attr "mode" "DI")])
6766
6767 (define_insn "*bmi2_umulsidi3_1"
6768   [(set (match_operand:SI 0 "register_operand" "=r")
6769         (mult:SI
6770           (match_operand:SI 2 "nonimmediate_operand" "%d")
6771           (match_operand:SI 3 "nonimmediate_operand" "rm")))
6772    (set (match_operand:SI 1 "register_operand" "=r")
6773         (truncate:SI
6774           (lshiftrt:DI
6775             (mult:DI (zero_extend:DI (match_dup 2))
6776                      (zero_extend:DI (match_dup 3)))
6777             (const_int 32))))]
6778   "!TARGET_64BIT && TARGET_BMI2
6779    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6780   "mulx\t{%3, %0, %1|%1, %0, %3}"
6781   [(set_attr "type" "imulx")
6782    (set_attr "prefix" "vex")
6783    (set_attr "mode" "SI")])
6784
6785 (define_insn "*umul<mode><dwi>3_1"
6786   [(set (match_operand:<DWI> 0 "register_operand" "=A,r")
6787         (mult:<DWI>
6788           (zero_extend:<DWI>
6789             (match_operand:DWIH 1 "nonimmediate_operand" "%0,d"))
6790           (zero_extend:<DWI>
6791             (match_operand:DWIH 2 "nonimmediate_operand" "rm,rm"))))
6792    (clobber (reg:CC FLAGS_REG))]
6793   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6794   "@
6795    mul{<imodesuffix>}\t%2
6796    #"
6797   [(set_attr "isa" "*,bmi2")
6798    (set_attr "type" "imul,imulx")
6799    (set_attr "length_immediate" "0,*")
6800    (set (attr "athlon_decode")
6801         (cond [(eq_attr "alternative" "0")
6802                  (if_then_else (eq_attr "cpu" "athlon")
6803                    (const_string "vector")
6804                    (const_string "double"))]
6805               (const_string "*")))
6806    (set_attr "amdfam10_decode" "double,*")
6807    (set_attr "bdver1_decode" "direct,*")
6808    (set_attr "prefix" "orig,vex")
6809    (set_attr "mode" "<MODE>")])
6810
6811 ;; Convert mul to the mulx pattern to avoid flags dependency.
6812 (define_split
6813  [(set (match_operand:<DWI> 0 "register_operand" "")
6814        (mult:<DWI>
6815          (zero_extend:<DWI>
6816            (match_operand:DWIH 1 "register_operand" ""))
6817          (zero_extend:<DWI>
6818            (match_operand:DWIH 2 "nonimmediate_operand" ""))))
6819   (clobber (reg:CC FLAGS_REG))]
6820  "TARGET_BMI2 && reload_completed
6821   && true_regnum (operands[1]) == DX_REG"
6822   [(parallel [(set (match_dup 3)
6823                    (mult:DWIH (match_dup 1) (match_dup 2)))
6824               (set (match_dup 4)
6825                    (truncate:DWIH
6826                      (lshiftrt:<DWI>
6827                        (mult:<DWI> (zero_extend:<DWI> (match_dup 1))
6828                                    (zero_extend:<DWI> (match_dup 2)))
6829                        (match_dup 5))))])]
6830 {
6831   split_double_mode (<DWI>mode, &operands[0], 1, &operands[3], &operands[4]);
6832
6833   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
6834 })
6835
6836 (define_insn "*mul<mode><dwi>3_1"
6837   [(set (match_operand:<DWI> 0 "register_operand" "=A")
6838         (mult:<DWI>
6839           (sign_extend:<DWI>
6840             (match_operand:DWIH 1 "nonimmediate_operand" "%0"))
6841           (sign_extend:<DWI>
6842             (match_operand:DWIH 2 "nonimmediate_operand" "rm"))))
6843    (clobber (reg:CC FLAGS_REG))]
6844   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6845   "imul{<imodesuffix>}\t%2"
6846   [(set_attr "type" "imul")
6847    (set_attr "length_immediate" "0")
6848    (set (attr "athlon_decode")
6849      (if_then_else (eq_attr "cpu" "athlon")
6850         (const_string "vector")
6851         (const_string "double")))
6852    (set_attr "amdfam10_decode" "double")
6853    (set_attr "bdver1_decode" "direct")
6854    (set_attr "mode" "<MODE>")])
6855
6856 (define_insn "*<u>mulqihi3_1"
6857   [(set (match_operand:HI 0 "register_operand" "=a")
6858         (mult:HI
6859           (any_extend:HI
6860             (match_operand:QI 1 "nonimmediate_operand" "%0"))
6861           (any_extend:HI
6862             (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6863    (clobber (reg:CC FLAGS_REG))]
6864   "TARGET_QIMODE_MATH
6865    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6866   "<sgnprefix>mul{b}\t%2"
6867   [(set_attr "type" "imul")
6868    (set_attr "length_immediate" "0")
6869    (set (attr "athlon_decode")
6870      (if_then_else (eq_attr "cpu" "athlon")
6871         (const_string "vector")
6872         (const_string "direct")))
6873    (set_attr "amdfam10_decode" "direct")
6874    (set_attr "bdver1_decode" "direct")
6875    (set_attr "mode" "QI")])
6876
6877 (define_expand "<s>mul<mode>3_highpart"
6878   [(parallel [(set (match_operand:SWI48 0 "register_operand" "")
6879                    (truncate:SWI48
6880                      (lshiftrt:<DWI>
6881                        (mult:<DWI>
6882                          (any_extend:<DWI>
6883                            (match_operand:SWI48 1 "nonimmediate_operand" ""))
6884                          (any_extend:<DWI>
6885                            (match_operand:SWI48 2 "register_operand" "")))
6886                        (match_dup 4))))
6887               (clobber (match_scratch:SWI48 3 ""))
6888               (clobber (reg:CC FLAGS_REG))])]
6889   ""
6890   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
6891
6892 (define_insn "*<s>muldi3_highpart_1"
6893   [(set (match_operand:DI 0 "register_operand" "=d")
6894         (truncate:DI
6895           (lshiftrt:TI
6896             (mult:TI
6897               (any_extend:TI
6898                 (match_operand:DI 1 "nonimmediate_operand" "%a"))
6899               (any_extend:TI
6900                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
6901             (const_int 64))))
6902    (clobber (match_scratch:DI 3 "=1"))
6903    (clobber (reg:CC FLAGS_REG))]
6904   "TARGET_64BIT
6905    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6906   "<sgnprefix>mul{q}\t%2"
6907   [(set_attr "type" "imul")
6908    (set_attr "length_immediate" "0")
6909    (set (attr "athlon_decode")
6910      (if_then_else (eq_attr "cpu" "athlon")
6911         (const_string "vector")
6912         (const_string "double")))
6913    (set_attr "amdfam10_decode" "double")
6914    (set_attr "bdver1_decode" "direct")
6915    (set_attr "mode" "DI")])
6916
6917 (define_insn "*<s>mulsi3_highpart_1"
6918   [(set (match_operand:SI 0 "register_operand" "=d")
6919         (truncate:SI
6920           (lshiftrt:DI
6921             (mult:DI
6922               (any_extend:DI
6923                 (match_operand:SI 1 "nonimmediate_operand" "%a"))
6924               (any_extend:DI
6925                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6926             (const_int 32))))
6927    (clobber (match_scratch:SI 3 "=1"))
6928    (clobber (reg:CC FLAGS_REG))]
6929   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6930   "<sgnprefix>mul{l}\t%2"
6931   [(set_attr "type" "imul")
6932    (set_attr "length_immediate" "0")
6933    (set (attr "athlon_decode")
6934      (if_then_else (eq_attr "cpu" "athlon")
6935         (const_string "vector")
6936         (const_string "double")))
6937    (set_attr "amdfam10_decode" "double")
6938    (set_attr "bdver1_decode" "direct")
6939    (set_attr "mode" "SI")])
6940
6941 (define_insn "*<s>mulsi3_highpart_zext"
6942   [(set (match_operand:DI 0 "register_operand" "=d")
6943         (zero_extend:DI (truncate:SI
6944           (lshiftrt:DI
6945             (mult:DI (any_extend:DI
6946                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
6947                      (any_extend:DI
6948                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
6949             (const_int 32)))))
6950    (clobber (match_scratch:SI 3 "=1"))
6951    (clobber (reg:CC FLAGS_REG))]
6952   "TARGET_64BIT
6953    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6954   "<sgnprefix>mul{l}\t%2"
6955   [(set_attr "type" "imul")
6956    (set_attr "length_immediate" "0")
6957    (set (attr "athlon_decode")
6958      (if_then_else (eq_attr "cpu" "athlon")
6959         (const_string "vector")
6960         (const_string "double")))
6961    (set_attr "amdfam10_decode" "double")
6962    (set_attr "bdver1_decode" "direct")
6963    (set_attr "mode" "SI")])
6964
6965 ;; The patterns that match these are at the end of this file.
6966
6967 (define_expand "mulxf3"
6968   [(set (match_operand:XF 0 "register_operand" "")
6969         (mult:XF (match_operand:XF 1 "register_operand" "")
6970                  (match_operand:XF 2 "register_operand" "")))]
6971   "TARGET_80387")
6972
6973 (define_expand "mul<mode>3"
6974   [(set (match_operand:MODEF 0 "register_operand" "")
6975         (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
6976                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
6977   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
6978     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
6979 \f
6980 ;; Divide instructions
6981
6982 ;; The patterns that match these are at the end of this file.
6983
6984 (define_expand "divxf3"
6985   [(set (match_operand:XF 0 "register_operand" "")
6986         (div:XF (match_operand:XF 1 "register_operand" "")
6987                 (match_operand:XF 2 "register_operand" "")))]
6988   "TARGET_80387")
6989
6990 (define_expand "divdf3"
6991   [(set (match_operand:DF 0 "register_operand" "")
6992         (div:DF (match_operand:DF 1 "register_operand" "")
6993                 (match_operand:DF 2 "nonimmediate_operand" "")))]
6994    "(TARGET_80387 && X87_ENABLE_ARITH (DFmode))
6995     || (TARGET_SSE2 && TARGET_SSE_MATH)")
6996
6997 (define_expand "divsf3"
6998   [(set (match_operand:SF 0 "register_operand" "")
6999         (div:SF (match_operand:SF 1 "register_operand" "")
7000                 (match_operand:SF 2 "nonimmediate_operand" "")))]
7001   "(TARGET_80387 && X87_ENABLE_ARITH (SFmode))
7002     || TARGET_SSE_MATH"
7003 {
7004   if (TARGET_SSE_MATH
7005       && TARGET_RECIP_DIV
7006       && optimize_insn_for_speed_p ()
7007       && flag_finite_math_only && !flag_trapping_math
7008       && flag_unsafe_math_optimizations)
7009     {
7010       ix86_emit_swdivsf (operands[0], operands[1],
7011                          operands[2], SFmode);
7012       DONE;
7013     }
7014 })
7015 \f
7016 ;; Divmod instructions.
7017
7018 (define_expand "divmod<mode>4"
7019   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7020                    (div:SWIM248
7021                      (match_operand:SWIM248 1 "register_operand" "")
7022                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7023               (set (match_operand:SWIM248 3 "register_operand" "")
7024                    (mod:SWIM248 (match_dup 1) (match_dup 2)))
7025               (clobber (reg:CC FLAGS_REG))])])
7026
7027 ;; Split with 8bit unsigned divide:
7028 ;;      if (dividend an divisor are in [0-255])
7029 ;;         use 8bit unsigned integer divide
7030 ;;       else
7031 ;;         use original integer divide
7032 (define_split
7033   [(set (match_operand:SWI48 0 "register_operand" "")
7034         (div:SWI48 (match_operand:SWI48 2 "register_operand" "")
7035                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7036    (set (match_operand:SWI48 1 "register_operand" "")
7037         (mod:SWI48 (match_dup 2) (match_dup 3)))
7038    (clobber (reg:CC FLAGS_REG))]
7039   "TARGET_USE_8BIT_IDIV
7040    && TARGET_QIMODE_MATH
7041    && can_create_pseudo_p ()
7042    && !optimize_insn_for_size_p ()"
7043   [(const_int 0)]
7044   "ix86_split_idivmod (<MODE>mode, operands, true); DONE;")
7045
7046 (define_insn_and_split "divmod<mode>4_1"
7047   [(set (match_operand:SWI48 0 "register_operand" "=a")
7048         (div:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7049                    (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7050    (set (match_operand:SWI48 1 "register_operand" "=&d")
7051         (mod:SWI48 (match_dup 2) (match_dup 3)))
7052    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7053    (clobber (reg:CC FLAGS_REG))]
7054   ""
7055   "#"
7056   "reload_completed"
7057   [(parallel [(set (match_dup 1)
7058                    (ashiftrt:SWI48 (match_dup 4) (match_dup 5)))
7059               (clobber (reg:CC FLAGS_REG))])
7060    (parallel [(set (match_dup 0)
7061                    (div:SWI48 (match_dup 2) (match_dup 3)))
7062               (set (match_dup 1)
7063                    (mod:SWI48 (match_dup 2) (match_dup 3)))
7064               (use (match_dup 1))
7065               (clobber (reg:CC FLAGS_REG))])]
7066 {
7067   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7068
7069   if (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
7070     operands[4] = operands[2];
7071   else
7072     {
7073       /* Avoid use of cltd in favor of a mov+shift.  */
7074       emit_move_insn (operands[1], operands[2]);
7075       operands[4] = operands[1];
7076     }
7077 }
7078   [(set_attr "type" "multi")
7079    (set_attr "mode" "<MODE>")])
7080
7081 (define_insn_and_split "*divmod<mode>4"
7082   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7083         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7084                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7085    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7086         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7087    (clobber (reg:CC FLAGS_REG))]
7088   ""
7089   "#"
7090   "reload_completed"
7091   [(parallel [(set (match_dup 1)
7092                    (ashiftrt:SWIM248 (match_dup 4) (match_dup 5)))
7093               (clobber (reg:CC FLAGS_REG))])
7094    (parallel [(set (match_dup 0)
7095                    (div:SWIM248 (match_dup 2) (match_dup 3)))
7096               (set (match_dup 1)
7097                    (mod:SWIM248 (match_dup 2) (match_dup 3)))
7098               (use (match_dup 1))
7099               (clobber (reg:CC FLAGS_REG))])]
7100 {
7101   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7102
7103   if (<MODE>mode != HImode
7104       && (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD))
7105     operands[4] = operands[2];
7106   else
7107     {
7108       /* Avoid use of cltd in favor of a mov+shift.  */
7109       emit_move_insn (operands[1], operands[2]);
7110       operands[4] = operands[1];
7111     }
7112 }
7113   [(set_attr "type" "multi")
7114    (set_attr "mode" "<MODE>")])
7115
7116 (define_insn "*divmod<mode>4_noext"
7117   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7118         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7119                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7120    (set (match_operand:SWIM248 1 "register_operand" "=d")
7121         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7122    (use (match_operand:SWIM248 4 "register_operand" "1"))
7123    (clobber (reg:CC FLAGS_REG))]
7124   ""
7125   "idiv{<imodesuffix>}\t%3"
7126   [(set_attr "type" "idiv")
7127    (set_attr "mode" "<MODE>")])
7128
7129 (define_expand "divmodqi4"
7130   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7131                    (div:QI
7132                      (match_operand:QI 1 "register_operand" "")
7133                      (match_operand:QI 2 "nonimmediate_operand" "")))
7134               (set (match_operand:QI 3 "register_operand" "")
7135                    (mod:QI (match_dup 1) (match_dup 2)))
7136               (clobber (reg:CC FLAGS_REG))])]
7137   "TARGET_QIMODE_MATH"
7138 {
7139   rtx div, mod, insn;
7140   rtx tmp0, tmp1;
7141   
7142   tmp0 = gen_reg_rtx (HImode);
7143   tmp1 = gen_reg_rtx (HImode);
7144
7145   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7146      in AX.  */
7147   emit_insn (gen_extendqihi2 (tmp1, operands[1]));
7148   emit_insn (gen_divmodhiqi3 (tmp0, tmp1, operands[2]));
7149
7150   /* Extract remainder from AH.  */
7151   tmp1 = gen_rtx_SIGN_EXTRACT (QImode, tmp0, GEN_INT (8), GEN_INT (8));
7152   insn = emit_move_insn (operands[3], tmp1);
7153
7154   mod = gen_rtx_MOD (QImode, operands[1], operands[2]);
7155   set_unique_reg_note (insn, REG_EQUAL, mod);
7156
7157   /* Extract quotient from AL.  */
7158   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7159
7160   div = gen_rtx_DIV (QImode, operands[1], operands[2]);
7161   set_unique_reg_note (insn, REG_EQUAL, div);
7162
7163   DONE;
7164 })
7165
7166 ;; Divide AX by r/m8, with result stored in
7167 ;; AL <- Quotient
7168 ;; AH <- Remainder
7169 ;; Change div/mod to HImode and extend the second argument to HImode
7170 ;; so that mode of div/mod matches with mode of arguments.  Otherwise
7171 ;; combine may fail.
7172 (define_insn "divmodhiqi3"
7173   [(set (match_operand:HI 0 "register_operand" "=a")
7174         (ior:HI
7175           (ashift:HI
7176             (zero_extend:HI
7177               (truncate:QI
7178                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7179                         (sign_extend:HI
7180                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7181             (const_int 8))
7182           (zero_extend:HI
7183             (truncate:QI
7184               (div:HI (match_dup 1) (sign_extend:HI (match_dup 2)))))))
7185    (clobber (reg:CC FLAGS_REG))]
7186   "TARGET_QIMODE_MATH"
7187   "idiv{b}\t%2"
7188   [(set_attr "type" "idiv")
7189    (set_attr "mode" "QI")])
7190
7191 (define_expand "udivmod<mode>4"
7192   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7193                    (udiv:SWIM248
7194                      (match_operand:SWIM248 1 "register_operand" "")
7195                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7196               (set (match_operand:SWIM248 3 "register_operand" "")
7197                    (umod:SWIM248 (match_dup 1) (match_dup 2)))
7198               (clobber (reg:CC FLAGS_REG))])])
7199
7200 ;; Split with 8bit unsigned divide:
7201 ;;      if (dividend an divisor are in [0-255])
7202 ;;         use 8bit unsigned integer divide
7203 ;;       else
7204 ;;         use original integer divide
7205 (define_split
7206   [(set (match_operand:SWI48 0 "register_operand" "")
7207         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "")
7208                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7209    (set (match_operand:SWI48 1 "register_operand" "")
7210         (umod:SWI48 (match_dup 2) (match_dup 3)))
7211    (clobber (reg:CC FLAGS_REG))]
7212   "TARGET_USE_8BIT_IDIV
7213    && TARGET_QIMODE_MATH
7214    && can_create_pseudo_p ()
7215    && !optimize_insn_for_size_p ()"
7216   [(const_int 0)]
7217   "ix86_split_idivmod (<MODE>mode, operands, false); DONE;")
7218
7219 (define_insn_and_split "udivmod<mode>4_1"
7220   [(set (match_operand:SWI48 0 "register_operand" "=a")
7221         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7222                     (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7223    (set (match_operand:SWI48 1 "register_operand" "=&d")
7224         (umod:SWI48 (match_dup 2) (match_dup 3)))
7225    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7226    (clobber (reg:CC FLAGS_REG))]
7227   ""
7228   "#"
7229   "reload_completed"
7230   [(set (match_dup 1) (const_int 0))
7231    (parallel [(set (match_dup 0)
7232                    (udiv:SWI48 (match_dup 2) (match_dup 3)))
7233               (set (match_dup 1)
7234                    (umod:SWI48 (match_dup 2) (match_dup 3)))
7235               (use (match_dup 1))
7236               (clobber (reg:CC FLAGS_REG))])]
7237   ""
7238   [(set_attr "type" "multi")
7239    (set_attr "mode" "<MODE>")])
7240
7241 (define_insn_and_split "*udivmod<mode>4"
7242   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7243         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7244                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7245    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7246         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7247    (clobber (reg:CC FLAGS_REG))]
7248   ""
7249   "#"
7250   "reload_completed"
7251   [(set (match_dup 1) (const_int 0))
7252    (parallel [(set (match_dup 0)
7253                    (udiv:SWIM248 (match_dup 2) (match_dup 3)))
7254               (set (match_dup 1)
7255                    (umod:SWIM248 (match_dup 2) (match_dup 3)))
7256               (use (match_dup 1))
7257               (clobber (reg:CC FLAGS_REG))])]
7258   ""
7259   [(set_attr "type" "multi")
7260    (set_attr "mode" "<MODE>")])
7261
7262 (define_insn "*udivmod<mode>4_noext"
7263   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7264         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7265                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7266    (set (match_operand:SWIM248 1 "register_operand" "=d")
7267         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7268    (use (match_operand:SWIM248 4 "register_operand" "1"))
7269    (clobber (reg:CC FLAGS_REG))]
7270   ""
7271   "div{<imodesuffix>}\t%3"
7272   [(set_attr "type" "idiv")
7273    (set_attr "mode" "<MODE>")])
7274
7275 (define_expand "udivmodqi4"
7276   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7277                    (udiv:QI
7278                      (match_operand:QI 1 "register_operand" "")
7279                      (match_operand:QI 2 "nonimmediate_operand" "")))
7280               (set (match_operand:QI 3 "register_operand" "")
7281                    (umod:QI (match_dup 1) (match_dup 2)))
7282               (clobber (reg:CC FLAGS_REG))])]
7283   "TARGET_QIMODE_MATH"
7284 {
7285   rtx div, mod, insn;
7286   rtx tmp0, tmp1;
7287   
7288   tmp0 = gen_reg_rtx (HImode);
7289   tmp1 = gen_reg_rtx (HImode);
7290
7291   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7292      in AX.  */
7293   emit_insn (gen_zero_extendqihi2 (tmp1, operands[1]));
7294   emit_insn (gen_udivmodhiqi3 (tmp0, tmp1, operands[2]));
7295
7296   /* Extract remainder from AH.  */
7297   tmp1 = gen_rtx_ZERO_EXTRACT (SImode, tmp0, GEN_INT (8), GEN_INT (8));
7298   tmp1 = simplify_gen_subreg (QImode, tmp1, SImode, 0);
7299   insn = emit_move_insn (operands[3], tmp1);
7300
7301   mod = gen_rtx_UMOD (QImode, operands[1], operands[2]);
7302   set_unique_reg_note (insn, REG_EQUAL, mod);
7303
7304   /* Extract quotient from AL.  */
7305   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7306
7307   div = gen_rtx_UDIV (QImode, operands[1], operands[2]);
7308   set_unique_reg_note (insn, REG_EQUAL, div);
7309
7310   DONE;
7311 })
7312
7313 (define_insn "udivmodhiqi3"
7314   [(set (match_operand:HI 0 "register_operand" "=a")
7315         (ior:HI
7316           (ashift:HI
7317             (zero_extend:HI
7318               (truncate:QI
7319                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7320                         (zero_extend:HI
7321                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7322             (const_int 8))
7323           (zero_extend:HI
7324             (truncate:QI
7325               (div:HI (match_dup 1) (zero_extend:HI (match_dup 2)))))))
7326    (clobber (reg:CC FLAGS_REG))]
7327   "TARGET_QIMODE_MATH"
7328   "div{b}\t%2"
7329   [(set_attr "type" "idiv")
7330    (set_attr "mode" "QI")])
7331
7332 ;; We cannot use div/idiv for double division, because it causes
7333 ;; "division by zero" on the overflow and that's not what we expect
7334 ;; from truncate.  Because true (non truncating) double division is
7335 ;; never generated, we can't create this insn anyway.
7336 ;
7337 ;(define_insn ""
7338 ;  [(set (match_operand:SI 0 "register_operand" "=a")
7339 ;       (truncate:SI
7340 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
7341 ;                  (zero_extend:DI
7342 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7343 ;   (set (match_operand:SI 3 "register_operand" "=d")
7344 ;       (truncate:SI
7345 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7346 ;   (clobber (reg:CC FLAGS_REG))]
7347 ;  ""
7348 ;  "div{l}\t{%2, %0|%0, %2}"
7349 ;  [(set_attr "type" "idiv")])
7350 \f
7351 ;;- Logical AND instructions
7352
7353 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7354 ;; Note that this excludes ah.
7355
7356 (define_expand "testsi_ccno_1"
7357   [(set (reg:CCNO FLAGS_REG)
7358         (compare:CCNO
7359           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7360                   (match_operand:SI 1 "x86_64_nonmemory_operand" ""))
7361           (const_int 0)))])
7362
7363 (define_expand "testqi_ccz_1"
7364   [(set (reg:CCZ FLAGS_REG)
7365         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7366                              (match_operand:QI 1 "nonmemory_operand" ""))
7367                  (const_int 0)))])
7368
7369 (define_expand "testdi_ccno_1"
7370   [(set (reg:CCNO FLAGS_REG)
7371         (compare:CCNO
7372           (and:DI (match_operand:DI 0 "nonimmediate_operand" "")
7373                   (match_operand:DI 1 "x86_64_szext_general_operand" ""))
7374           (const_int 0)))]
7375   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))")
7376
7377 (define_insn "*testdi_1"
7378   [(set (reg FLAGS_REG)
7379         (compare
7380          (and:DI
7381           (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7382           (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7383          (const_int 0)))]
7384   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7385    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7386   "@
7387    test{l}\t{%k1, %k0|%k0, %k1}
7388    test{l}\t{%k1, %k0|%k0, %k1}
7389    test{q}\t{%1, %0|%0, %1}
7390    test{q}\t{%1, %0|%0, %1}
7391    test{q}\t{%1, %0|%0, %1}"
7392   [(set_attr "type" "test")
7393    (set_attr "modrm" "0,1,0,1,1")
7394    (set_attr "mode" "SI,SI,DI,DI,DI")])
7395
7396 (define_insn "*testqi_1_maybe_si"
7397   [(set (reg FLAGS_REG)
7398         (compare
7399           (and:QI
7400             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7401             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7402           (const_int 0)))]
7403    "!(MEM_P (operands[0]) && MEM_P (operands[1]))
7404     && ix86_match_ccmode (insn,
7405                          CONST_INT_P (operands[1])
7406                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7407 {
7408   if (which_alternative == 3)
7409     {
7410       if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
7411         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7412       return "test{l}\t{%1, %k0|%k0, %1}";
7413     }
7414   return "test{b}\t{%1, %0|%0, %1}";
7415 }
7416   [(set_attr "type" "test")
7417    (set_attr "modrm" "0,1,1,1")
7418    (set_attr "mode" "QI,QI,QI,SI")
7419    (set_attr "pent_pair" "uv,np,uv,np")])
7420
7421 (define_insn "*test<mode>_1"
7422   [(set (reg FLAGS_REG)
7423         (compare
7424          (and:SWI124
7425           (match_operand:SWI124 0 "nonimmediate_operand" "%!*a,<r>,<r>m")
7426           (match_operand:SWI124 1 "<general_operand>" "<i>,<i>,<r><i>"))
7427          (const_int 0)))]
7428   "ix86_match_ccmode (insn, CCNOmode)
7429    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7430   "test{<imodesuffix>}\t{%1, %0|%0, %1}"
7431   [(set_attr "type" "test")
7432    (set_attr "modrm" "0,1,1")
7433    (set_attr "mode" "<MODE>")
7434    (set_attr "pent_pair" "uv,np,uv")])
7435
7436 (define_expand "testqi_ext_ccno_0"
7437   [(set (reg:CCNO FLAGS_REG)
7438         (compare:CCNO
7439           (and:SI
7440             (zero_extract:SI
7441               (match_operand 0 "ext_register_operand" "")
7442               (const_int 8)
7443               (const_int 8))
7444             (match_operand 1 "const_int_operand" ""))
7445           (const_int 0)))])
7446
7447 (define_insn "*testqi_ext_0"
7448   [(set (reg FLAGS_REG)
7449         (compare
7450           (and:SI
7451             (zero_extract:SI
7452               (match_operand 0 "ext_register_operand" "Q")
7453               (const_int 8)
7454               (const_int 8))
7455             (match_operand 1 "const_int_operand" "n"))
7456           (const_int 0)))]
7457   "ix86_match_ccmode (insn, CCNOmode)"
7458   "test{b}\t{%1, %h0|%h0, %1}"
7459   [(set_attr "type" "test")
7460    (set_attr "mode" "QI")
7461    (set_attr "length_immediate" "1")
7462    (set_attr "modrm" "1")
7463    (set_attr "pent_pair" "np")])
7464
7465 (define_insn "*testqi_ext_1_rex64"
7466   [(set (reg FLAGS_REG)
7467         (compare
7468           (and:SI
7469             (zero_extract:SI
7470               (match_operand 0 "ext_register_operand" "Q")
7471               (const_int 8)
7472               (const_int 8))
7473             (zero_extend:SI
7474               (match_operand:QI 1 "register_operand" "Q")))
7475           (const_int 0)))]
7476   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7477   "test{b}\t{%1, %h0|%h0, %1}"
7478   [(set_attr "type" "test")
7479    (set_attr "mode" "QI")])
7480
7481 (define_insn "*testqi_ext_1"
7482   [(set (reg FLAGS_REG)
7483         (compare
7484           (and:SI
7485             (zero_extract:SI
7486               (match_operand 0 "ext_register_operand" "Q")
7487               (const_int 8)
7488               (const_int 8))
7489             (zero_extend:SI
7490               (match_operand:QI 1 "general_operand" "Qm")))
7491           (const_int 0)))]
7492   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7493   "test{b}\t{%1, %h0|%h0, %1}"
7494   [(set_attr "type" "test")
7495    (set_attr "mode" "QI")])
7496
7497 (define_insn "*testqi_ext_2"
7498   [(set (reg FLAGS_REG)
7499         (compare
7500           (and:SI
7501             (zero_extract:SI
7502               (match_operand 0 "ext_register_operand" "Q")
7503               (const_int 8)
7504               (const_int 8))
7505             (zero_extract:SI
7506               (match_operand 1 "ext_register_operand" "Q")
7507               (const_int 8)
7508               (const_int 8)))
7509           (const_int 0)))]
7510   "ix86_match_ccmode (insn, CCNOmode)"
7511   "test{b}\t{%h1, %h0|%h0, %h1}"
7512   [(set_attr "type" "test")
7513    (set_attr "mode" "QI")])
7514
7515 (define_insn "*testqi_ext_3_rex64"
7516   [(set (reg FLAGS_REG)
7517         (compare (zero_extract:DI
7518                    (match_operand 0 "nonimmediate_operand" "rm")
7519                    (match_operand:DI 1 "const_int_operand" "")
7520                    (match_operand:DI 2 "const_int_operand" ""))
7521                  (const_int 0)))]
7522   "TARGET_64BIT
7523    && ix86_match_ccmode (insn, CCNOmode)
7524    && INTVAL (operands[1]) > 0
7525    && INTVAL (operands[2]) >= 0
7526    /* Ensure that resulting mask is zero or sign extended operand.  */
7527    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7528        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7529            && INTVAL (operands[1]) > 32))
7530    && (GET_MODE (operands[0]) == SImode
7531        || GET_MODE (operands[0]) == DImode
7532        || GET_MODE (operands[0]) == HImode
7533        || GET_MODE (operands[0]) == QImode)"
7534   "#")
7535
7536 ;; Combine likes to form bit extractions for some tests.  Humor it.
7537 (define_insn "*testqi_ext_3"
7538   [(set (reg FLAGS_REG)
7539         (compare (zero_extract:SI
7540                    (match_operand 0 "nonimmediate_operand" "rm")
7541                    (match_operand:SI 1 "const_int_operand" "")
7542                    (match_operand:SI 2 "const_int_operand" ""))
7543                  (const_int 0)))]
7544   "ix86_match_ccmode (insn, CCNOmode)
7545    && INTVAL (operands[1]) > 0
7546    && INTVAL (operands[2]) >= 0
7547    && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7548    && (GET_MODE (operands[0]) == SImode
7549        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7550        || GET_MODE (operands[0]) == HImode
7551        || GET_MODE (operands[0]) == QImode)"
7552   "#")
7553
7554 (define_split
7555   [(set (match_operand 0 "flags_reg_operand" "")
7556         (match_operator 1 "compare_operator"
7557           [(zero_extract
7558              (match_operand 2 "nonimmediate_operand" "")
7559              (match_operand 3 "const_int_operand" "")
7560              (match_operand 4 "const_int_operand" ""))
7561            (const_int 0)]))]
7562   "ix86_match_ccmode (insn, CCNOmode)"
7563   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7564 {
7565   rtx val = operands[2];
7566   HOST_WIDE_INT len = INTVAL (operands[3]);
7567   HOST_WIDE_INT pos = INTVAL (operands[4]);
7568   HOST_WIDE_INT mask;
7569   enum machine_mode mode, submode;
7570
7571   mode = GET_MODE (val);
7572   if (MEM_P (val))
7573     {
7574       /* ??? Combine likes to put non-volatile mem extractions in QImode
7575          no matter the size of the test.  So find a mode that works.  */
7576       if (! MEM_VOLATILE_P (val))
7577         {
7578           mode = smallest_mode_for_size (pos + len, MODE_INT);
7579           val = adjust_address (val, mode, 0);
7580         }
7581     }
7582   else if (GET_CODE (val) == SUBREG
7583            && (submode = GET_MODE (SUBREG_REG (val)),
7584                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7585            && pos + len <= GET_MODE_BITSIZE (submode)
7586            && GET_MODE_CLASS (submode) == MODE_INT)
7587     {
7588       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
7589       mode = submode;
7590       val = SUBREG_REG (val);
7591     }
7592   else if (mode == HImode && pos + len <= 8)
7593     {
7594       /* Small HImode tests can be converted to QImode.  */
7595       mode = QImode;
7596       val = gen_lowpart (QImode, val);
7597     }
7598
7599   if (len == HOST_BITS_PER_WIDE_INT)
7600     mask = -1;
7601   else
7602     mask = ((HOST_WIDE_INT)1 << len) - 1;
7603   mask <<= pos;
7604
7605   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7606 })
7607
7608 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7609 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7610 ;; this is relatively important trick.
7611 ;; Do the conversion only post-reload to avoid limiting of the register class
7612 ;; to QI regs.
7613 (define_split
7614   [(set (match_operand 0 "flags_reg_operand" "")
7615         (match_operator 1 "compare_operator"
7616           [(and (match_operand 2 "register_operand" "")
7617                 (match_operand 3 "const_int_operand" ""))
7618            (const_int 0)]))]
7619    "reload_completed
7620     && QI_REG_P (operands[2])
7621     && GET_MODE (operands[2]) != QImode
7622     && ((ix86_match_ccmode (insn, CCZmode)
7623          && !(INTVAL (operands[3]) & ~(255 << 8)))
7624         || (ix86_match_ccmode (insn, CCNOmode)
7625             && !(INTVAL (operands[3]) & ~(127 << 8))))"
7626   [(set (match_dup 0)
7627         (match_op_dup 1
7628           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7629                    (match_dup 3))
7630            (const_int 0)]))]
7631 {
7632   operands[2] = gen_lowpart (SImode, operands[2]);
7633   operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);
7634 })
7635
7636 (define_split
7637   [(set (match_operand 0 "flags_reg_operand" "")
7638         (match_operator 1 "compare_operator"
7639           [(and (match_operand 2 "nonimmediate_operand" "")
7640                 (match_operand 3 "const_int_operand" ""))
7641            (const_int 0)]))]
7642    "reload_completed
7643     && GET_MODE (operands[2]) != QImode
7644     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7645     && ((ix86_match_ccmode (insn, CCZmode)
7646          && !(INTVAL (operands[3]) & ~255))
7647         || (ix86_match_ccmode (insn, CCNOmode)
7648             && !(INTVAL (operands[3]) & ~127)))"
7649   [(set (match_dup 0)
7650         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7651                          (const_int 0)]))]
7652 {
7653   operands[2] = gen_lowpart (QImode, operands[2]);
7654   operands[3] = gen_lowpart (QImode, operands[3]);
7655 })
7656
7657 ;; %%% This used to optimize known byte-wide and operations to memory,
7658 ;; and sometimes to QImode registers.  If this is considered useful,
7659 ;; it should be done with splitters.
7660
7661 (define_expand "and<mode>3"
7662   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
7663         (and:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
7664                   (match_operand:SWIM 2 "<general_szext_operand>" "")))]
7665   ""
7666 {
7667   if (<MODE>mode == DImode
7668       && GET_CODE (operands[2]) == CONST_INT
7669       && INTVAL (operands[2]) == (HOST_WIDE_INT) 0xffffffff
7670       && REG_P (operands[1]))
7671     emit_insn (gen_zero_extendsidi2 (operands[0],
7672                                      gen_lowpart (SImode, operands[1])));
7673   else
7674     ix86_expand_binary_operator (AND, <MODE>mode, operands);
7675   DONE;
7676 })
7677
7678 (define_insn "*anddi_1"
7679   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
7680         (and:DI
7681          (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
7682          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
7683    (clobber (reg:CC FLAGS_REG))]
7684   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
7685 {
7686   switch (get_attr_type (insn))
7687     {
7688     case TYPE_IMOVX:
7689       {
7690         enum machine_mode mode;
7691
7692         gcc_assert (CONST_INT_P (operands[2]));
7693         if (INTVAL (operands[2]) == (HOST_WIDE_INT) 0xffffffff)
7694           mode = SImode;
7695         else if (INTVAL (operands[2]) == 0xffff)
7696           mode = HImode;
7697         else
7698           {
7699             gcc_assert (INTVAL (operands[2]) == 0xff);
7700             mode = QImode;
7701           }
7702
7703         operands[1] = gen_lowpart (mode, operands[1]);
7704         if (mode == SImode)
7705           return "mov{l}\t{%1, %k0|%k0, %1}";
7706         else if (mode == HImode)
7707           return "movz{wl|x}\t{%1, %k0|%k0, %1}";
7708         else
7709           return "movz{bl|x}\t{%1, %k0|%k0, %1}";
7710       }
7711
7712     default:
7713       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7714       if (get_attr_mode (insn) == MODE_SI)
7715         return "and{l}\t{%k2, %k0|%k0, %k2}";
7716       else
7717         return "and{q}\t{%2, %0|%0, %2}";
7718     }
7719 }
7720   [(set_attr "type" "alu,alu,alu,imovx")
7721    (set_attr "length_immediate" "*,*,*,0")
7722    (set (attr "prefix_rex")
7723      (if_then_else
7724        (and (eq_attr "type" "imovx")
7725             (and (match_test "INTVAL (operands[2]) == 0xff")
7726                  (match_operand 1 "ext_QIreg_operand" "")))
7727        (const_string "1")
7728        (const_string "*")))
7729    (set_attr "mode" "SI,DI,DI,SI")])
7730
7731 (define_insn "*andsi_1"
7732   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7733         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7734                 (match_operand:SI 2 "x86_64_general_operand" "re,rm,L")))
7735    (clobber (reg:CC FLAGS_REG))]
7736   "ix86_binary_operator_ok (AND, SImode, operands)"
7737 {
7738   switch (get_attr_type (insn))
7739     {
7740     case TYPE_IMOVX:
7741       {
7742         enum machine_mode mode;
7743
7744         gcc_assert (CONST_INT_P (operands[2]));
7745         if (INTVAL (operands[2]) == 0xffff)
7746           mode = HImode;
7747         else
7748           {
7749             gcc_assert (INTVAL (operands[2]) == 0xff);
7750             mode = QImode;
7751           }
7752
7753         operands[1] = gen_lowpart (mode, operands[1]);
7754         if (mode == HImode)
7755           return "movz{wl|x}\t{%1, %0|%0, %1}";
7756         else
7757           return "movz{bl|x}\t{%1, %0|%0, %1}";
7758       }
7759
7760     default:
7761       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7762       return "and{l}\t{%2, %0|%0, %2}";
7763     }
7764 }
7765   [(set_attr "type" "alu,alu,imovx")
7766    (set (attr "prefix_rex")
7767      (if_then_else
7768        (and (eq_attr "type" "imovx")
7769             (and (match_test "INTVAL (operands[2]) == 0xff")
7770                  (match_operand 1 "ext_QIreg_operand" "")))
7771        (const_string "1")
7772        (const_string "*")))
7773    (set_attr "length_immediate" "*,*,0")
7774    (set_attr "mode" "SI")])
7775
7776 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7777 (define_insn "*andsi_1_zext"
7778   [(set (match_operand:DI 0 "register_operand" "=r")
7779         (zero_extend:DI
7780           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7781                   (match_operand:SI 2 "x86_64_general_operand" "rme"))))
7782    (clobber (reg:CC FLAGS_REG))]
7783   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
7784   "and{l}\t{%2, %k0|%k0, %2}"
7785   [(set_attr "type" "alu")
7786    (set_attr "mode" "SI")])
7787
7788 (define_insn "*andhi_1"
7789   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
7790         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
7791                 (match_operand:HI 2 "general_operand" "rn,rm,L")))
7792    (clobber (reg:CC FLAGS_REG))]
7793   "ix86_binary_operator_ok (AND, HImode, operands)"
7794 {
7795   switch (get_attr_type (insn))
7796     {
7797     case TYPE_IMOVX:
7798       gcc_assert (CONST_INT_P (operands[2]));
7799       gcc_assert (INTVAL (operands[2]) == 0xff);
7800       return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
7801
7802     default:
7803       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7804
7805       return "and{w}\t{%2, %0|%0, %2}";
7806     }
7807 }
7808   [(set_attr "type" "alu,alu,imovx")
7809    (set_attr "length_immediate" "*,*,0")
7810    (set (attr "prefix_rex")
7811      (if_then_else
7812        (and (eq_attr "type" "imovx")
7813             (match_operand 1 "ext_QIreg_operand" ""))
7814        (const_string "1")
7815        (const_string "*")))
7816    (set_attr "mode" "HI,HI,SI")])
7817
7818 ;; %%% Potential partial reg stall on alternative 2.  What to do?
7819 (define_insn "*andqi_1"
7820   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
7821         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7822                 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
7823    (clobber (reg:CC FLAGS_REG))]
7824   "ix86_binary_operator_ok (AND, QImode, operands)"
7825   "@
7826    and{b}\t{%2, %0|%0, %2}
7827    and{b}\t{%2, %0|%0, %2}
7828    and{l}\t{%k2, %k0|%k0, %k2}"
7829   [(set_attr "type" "alu")
7830    (set_attr "mode" "QI,QI,SI")])
7831
7832 (define_insn "*andqi_1_slp"
7833   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7834         (and:QI (match_dup 0)
7835                 (match_operand:QI 1 "general_operand" "qn,qmn")))
7836    (clobber (reg:CC FLAGS_REG))]
7837   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7838    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7839   "and{b}\t{%1, %0|%0, %1}"
7840   [(set_attr "type" "alu1")
7841    (set_attr "mode" "QI")])
7842
7843 (define_split
7844   [(set (match_operand 0 "register_operand" "")
7845         (and (match_dup 0)
7846              (const_int -65536)))
7847    (clobber (reg:CC FLAGS_REG))]
7848   "(TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)
7849     || optimize_function_for_size_p (cfun)"
7850   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7851   "operands[1] = gen_lowpart (HImode, operands[0]);")
7852
7853 (define_split
7854   [(set (match_operand 0 "ext_register_operand" "")
7855         (and (match_dup 0)
7856              (const_int -256)))
7857    (clobber (reg:CC FLAGS_REG))]
7858   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7859    && reload_completed"
7860   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7861   "operands[1] = gen_lowpart (QImode, operands[0]);")
7862
7863 (define_split
7864   [(set (match_operand 0 "ext_register_operand" "")
7865         (and (match_dup 0)
7866              (const_int -65281)))
7867    (clobber (reg:CC FLAGS_REG))]
7868   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7869    && reload_completed"
7870   [(parallel [(set (zero_extract:SI (match_dup 0)
7871                                     (const_int 8)
7872                                     (const_int 8))
7873                    (xor:SI
7874                      (zero_extract:SI (match_dup 0)
7875                                       (const_int 8)
7876                                       (const_int 8))
7877                      (zero_extract:SI (match_dup 0)
7878                                       (const_int 8)
7879                                       (const_int 8))))
7880               (clobber (reg:CC FLAGS_REG))])]
7881   "operands[0] = gen_lowpart (SImode, operands[0]);")
7882
7883 (define_insn "*anddi_2"
7884   [(set (reg FLAGS_REG)
7885         (compare
7886          (and:DI
7887           (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
7888           (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
7889          (const_int 0)))
7890    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
7891         (and:DI (match_dup 1) (match_dup 2)))]
7892   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7893    && ix86_binary_operator_ok (AND, DImode, operands)"
7894   "@
7895    and{l}\t{%k2, %k0|%k0, %k2}
7896    and{q}\t{%2, %0|%0, %2}
7897    and{q}\t{%2, %0|%0, %2}"
7898   [(set_attr "type" "alu")
7899    (set_attr "mode" "SI,DI,DI")])
7900
7901 (define_insn "*andqi_2_maybe_si"
7902   [(set (reg FLAGS_REG)
7903         (compare (and:QI
7904                   (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7905                   (match_operand:QI 2 "general_operand" "qmn,qn,n"))
7906                  (const_int 0)))
7907    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
7908         (and:QI (match_dup 1) (match_dup 2)))]
7909   "ix86_binary_operator_ok (AND, QImode, operands)
7910    && ix86_match_ccmode (insn,
7911                          CONST_INT_P (operands[2])
7912                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
7913 {
7914   if (which_alternative == 2)
7915     {
7916       if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
7917         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
7918       return "and{l}\t{%2, %k0|%k0, %2}";
7919     }
7920   return "and{b}\t{%2, %0|%0, %2}";
7921 }
7922   [(set_attr "type" "alu")
7923    (set_attr "mode" "QI,QI,SI")])
7924
7925 (define_insn "*and<mode>_2"
7926   [(set (reg FLAGS_REG)
7927         (compare (and:SWI124
7928                   (match_operand:SWI124 1 "nonimmediate_operand" "%0,0")
7929                   (match_operand:SWI124 2 "<general_operand>" "<g>,<r><i>"))
7930                  (const_int 0)))
7931    (set (match_operand:SWI124 0 "nonimmediate_operand" "=<r>,<r>m")
7932         (and:SWI124 (match_dup 1) (match_dup 2)))]
7933   "ix86_match_ccmode (insn, CCNOmode)
7934    && ix86_binary_operator_ok (AND, <MODE>mode, operands)"
7935   "and{<imodesuffix>}\t{%2, %0|%0, %2}"
7936   [(set_attr "type" "alu")
7937    (set_attr "mode" "<MODE>")])
7938
7939 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7940 (define_insn "*andsi_2_zext"
7941   [(set (reg FLAGS_REG)
7942         (compare (and:SI
7943                   (match_operand:SI 1 "nonimmediate_operand" "%0")
7944                   (match_operand:SI 2 "x86_64_general_operand" "rme"))
7945                  (const_int 0)))
7946    (set (match_operand:DI 0 "register_operand" "=r")
7947         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
7948   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7949    && ix86_binary_operator_ok (AND, SImode, operands)"
7950   "and{l}\t{%2, %k0|%k0, %2}"
7951   [(set_attr "type" "alu")
7952    (set_attr "mode" "SI")])
7953
7954 (define_insn "*andqi_2_slp"
7955   [(set (reg FLAGS_REG)
7956         (compare (and:QI
7957                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
7958                    (match_operand:QI 1 "nonimmediate_operand" "qmn,qn"))
7959                  (const_int 0)))
7960    (set (strict_low_part (match_dup 0))
7961         (and:QI (match_dup 0) (match_dup 1)))]
7962   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7963    && ix86_match_ccmode (insn, CCNOmode)
7964    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7965   "and{b}\t{%1, %0|%0, %1}"
7966   [(set_attr "type" "alu1")
7967    (set_attr "mode" "QI")])
7968
7969 ;; ??? A bug in recog prevents it from recognizing a const_int as an
7970 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
7971 ;; for a QImode operand, which of course failed.
7972 (define_insn "andqi_ext_0"
7973   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7974                          (const_int 8)
7975                          (const_int 8))
7976         (and:SI
7977           (zero_extract:SI
7978             (match_operand 1 "ext_register_operand" "0")
7979             (const_int 8)
7980             (const_int 8))
7981           (match_operand 2 "const_int_operand" "n")))
7982    (clobber (reg:CC FLAGS_REG))]
7983   ""
7984   "and{b}\t{%2, %h0|%h0, %2}"
7985   [(set_attr "type" "alu")
7986    (set_attr "length_immediate" "1")
7987    (set_attr "modrm" "1")
7988    (set_attr "mode" "QI")])
7989
7990 ;; Generated by peephole translating test to and.  This shows up
7991 ;; often in fp comparisons.
7992 (define_insn "*andqi_ext_0_cc"
7993   [(set (reg FLAGS_REG)
7994         (compare
7995           (and:SI
7996             (zero_extract:SI
7997               (match_operand 1 "ext_register_operand" "0")
7998               (const_int 8)
7999               (const_int 8))
8000             (match_operand 2 "const_int_operand" "n"))
8001           (const_int 0)))
8002    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8003                          (const_int 8)
8004                          (const_int 8))
8005         (and:SI
8006           (zero_extract:SI
8007             (match_dup 1)
8008             (const_int 8)
8009             (const_int 8))
8010           (match_dup 2)))]
8011   "ix86_match_ccmode (insn, CCNOmode)"
8012   "and{b}\t{%2, %h0|%h0, %2}"
8013   [(set_attr "type" "alu")
8014    (set_attr "length_immediate" "1")
8015    (set_attr "modrm" "1")
8016    (set_attr "mode" "QI")])
8017
8018 (define_insn "*andqi_ext_1_rex64"
8019   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8020                          (const_int 8)
8021                          (const_int 8))
8022         (and:SI
8023           (zero_extract:SI
8024             (match_operand 1 "ext_register_operand" "0")
8025             (const_int 8)
8026             (const_int 8))
8027           (zero_extend:SI
8028             (match_operand 2 "ext_register_operand" "Q"))))
8029    (clobber (reg:CC FLAGS_REG))]
8030   "TARGET_64BIT"
8031   "and{b}\t{%2, %h0|%h0, %2}"
8032   [(set_attr "type" "alu")
8033    (set_attr "length_immediate" "0")
8034    (set_attr "mode" "QI")])
8035
8036 (define_insn "*andqi_ext_1"
8037   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8038                          (const_int 8)
8039                          (const_int 8))
8040         (and:SI
8041           (zero_extract:SI
8042             (match_operand 1 "ext_register_operand" "0")
8043             (const_int 8)
8044             (const_int 8))
8045           (zero_extend:SI
8046             (match_operand:QI 2 "general_operand" "Qm"))))
8047    (clobber (reg:CC FLAGS_REG))]
8048   "!TARGET_64BIT"
8049   "and{b}\t{%2, %h0|%h0, %2}"
8050   [(set_attr "type" "alu")
8051    (set_attr "length_immediate" "0")
8052    (set_attr "mode" "QI")])
8053
8054 (define_insn "*andqi_ext_2"
8055   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8056                          (const_int 8)
8057                          (const_int 8))
8058         (and:SI
8059           (zero_extract:SI
8060             (match_operand 1 "ext_register_operand" "%0")
8061             (const_int 8)
8062             (const_int 8))
8063           (zero_extract:SI
8064             (match_operand 2 "ext_register_operand" "Q")
8065             (const_int 8)
8066             (const_int 8))))
8067    (clobber (reg:CC FLAGS_REG))]
8068   ""
8069   "and{b}\t{%h2, %h0|%h0, %h2}"
8070   [(set_attr "type" "alu")
8071    (set_attr "length_immediate" "0")
8072    (set_attr "mode" "QI")])
8073
8074 ;; Convert wide AND instructions with immediate operand to shorter QImode
8075 ;; equivalents when possible.
8076 ;; Don't do the splitting with memory operands, since it introduces risk
8077 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
8078 ;; for size, but that can (should?) be handled by generic code instead.
8079 (define_split
8080   [(set (match_operand 0 "register_operand" "")
8081         (and (match_operand 1 "register_operand" "")
8082              (match_operand 2 "const_int_operand" "")))
8083    (clobber (reg:CC FLAGS_REG))]
8084    "reload_completed
8085     && QI_REG_P (operands[0])
8086     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8087     && !(~INTVAL (operands[2]) & ~(255 << 8))
8088     && GET_MODE (operands[0]) != QImode"
8089   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8090                    (and:SI (zero_extract:SI (match_dup 1)
8091                                             (const_int 8) (const_int 8))
8092                            (match_dup 2)))
8093               (clobber (reg:CC FLAGS_REG))])]
8094 {
8095   operands[0] = gen_lowpart (SImode, operands[0]);
8096   operands[1] = gen_lowpart (SImode, operands[1]);
8097   operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);
8098 })
8099
8100 ;; Since AND can be encoded with sign extended immediate, this is only
8101 ;; profitable when 7th bit is not set.
8102 (define_split
8103   [(set (match_operand 0 "register_operand" "")
8104         (and (match_operand 1 "general_operand" "")
8105              (match_operand 2 "const_int_operand" "")))
8106    (clobber (reg:CC FLAGS_REG))]
8107    "reload_completed
8108     && ANY_QI_REG_P (operands[0])
8109     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8110     && !(~INTVAL (operands[2]) & ~255)
8111     && !(INTVAL (operands[2]) & 128)
8112     && GET_MODE (operands[0]) != QImode"
8113   [(parallel [(set (strict_low_part (match_dup 0))
8114                    (and:QI (match_dup 1)
8115                            (match_dup 2)))
8116               (clobber (reg:CC FLAGS_REG))])]
8117 {
8118   operands[0] = gen_lowpart (QImode, operands[0]);
8119   operands[1] = gen_lowpart (QImode, operands[1]);
8120   operands[2] = gen_lowpart (QImode, operands[2]);
8121 })
8122 \f
8123 ;; Logical inclusive and exclusive OR instructions
8124
8125 ;; %%% This used to optimize known byte-wide and operations to memory.
8126 ;; If this is considered useful, it should be done with splitters.
8127
8128 (define_expand "<code><mode>3"
8129   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8130         (any_or:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
8131                      (match_operand:SWIM 2 "<general_operand>" "")))]
8132   ""
8133   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
8134
8135 (define_insn "*<code><mode>_1"
8136   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=r,rm")
8137         (any_or:SWI248
8138          (match_operand:SWI248 1 "nonimmediate_operand" "%0,0")
8139          (match_operand:SWI248 2 "<general_operand>" "<g>,r<i>")))
8140    (clobber (reg:CC FLAGS_REG))]
8141   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8142   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8143   [(set_attr "type" "alu")
8144    (set_attr "mode" "<MODE>")])
8145
8146 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8147 (define_insn "*<code>qi_1"
8148   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8149         (any_or:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8150                    (match_operand:QI 2 "general_operand" "qmn,qn,rn")))
8151    (clobber (reg:CC FLAGS_REG))]
8152   "ix86_binary_operator_ok (<CODE>, QImode, operands)"
8153   "@
8154    <logic>{b}\t{%2, %0|%0, %2}
8155    <logic>{b}\t{%2, %0|%0, %2}
8156    <logic>{l}\t{%k2, %k0|%k0, %k2}"
8157   [(set_attr "type" "alu")
8158    (set_attr "mode" "QI,QI,SI")])
8159
8160 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8161 (define_insn "*<code>si_1_zext"
8162   [(set (match_operand:DI 0 "register_operand" "=r")
8163         (zero_extend:DI
8164          (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8165                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
8166    (clobber (reg:CC FLAGS_REG))]
8167   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8168   "<logic>{l}\t{%2, %k0|%k0, %2}"
8169   [(set_attr "type" "alu")
8170    (set_attr "mode" "SI")])
8171
8172 (define_insn "*<code>si_1_zext_imm"
8173   [(set (match_operand:DI 0 "register_operand" "=r")
8174         (any_or:DI
8175          (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8176          (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8177    (clobber (reg:CC FLAGS_REG))]
8178   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8179   "<logic>{l}\t{%2, %k0|%k0, %2}"
8180   [(set_attr "type" "alu")
8181    (set_attr "mode" "SI")])
8182
8183 (define_insn "*<code>qi_1_slp"
8184   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8185         (any_or:QI (match_dup 0)
8186                    (match_operand:QI 1 "general_operand" "qmn,qn")))
8187    (clobber (reg:CC FLAGS_REG))]
8188   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8189    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8190   "<logic>{b}\t{%1, %0|%0, %1}"
8191   [(set_attr "type" "alu1")
8192    (set_attr "mode" "QI")])
8193
8194 (define_insn "*<code><mode>_2"
8195   [(set (reg FLAGS_REG)
8196         (compare (any_or:SWI
8197                   (match_operand:SWI 1 "nonimmediate_operand" "%0,0")
8198                   (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>"))
8199                  (const_int 0)))
8200    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m")
8201         (any_or:SWI (match_dup 1) (match_dup 2)))]
8202   "ix86_match_ccmode (insn, CCNOmode)
8203    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8204   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8205   [(set_attr "type" "alu")
8206    (set_attr "mode" "<MODE>")])
8207
8208 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8209 ;; ??? Special case for immediate operand is missing - it is tricky.
8210 (define_insn "*<code>si_2_zext"
8211   [(set (reg FLAGS_REG)
8212         (compare (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8213                             (match_operand:SI 2 "x86_64_general_operand" "rme"))
8214                  (const_int 0)))
8215    (set (match_operand:DI 0 "register_operand" "=r")
8216         (zero_extend:DI (any_or:SI (match_dup 1) (match_dup 2))))]
8217   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8218    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8219   "<logic>{l}\t{%2, %k0|%k0, %2}"
8220   [(set_attr "type" "alu")
8221    (set_attr "mode" "SI")])
8222
8223 (define_insn "*<code>si_2_zext_imm"
8224   [(set (reg FLAGS_REG)
8225         (compare (any_or:SI
8226                   (match_operand:SI 1 "nonimmediate_operand" "%0")
8227                   (match_operand:SI 2 "x86_64_zext_immediate_operand" "Z"))
8228                  (const_int 0)))
8229    (set (match_operand:DI 0 "register_operand" "=r")
8230         (any_or:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8231   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8232    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8233   "<logic>{l}\t{%2, %k0|%k0, %2}"
8234   [(set_attr "type" "alu")
8235    (set_attr "mode" "SI")])
8236
8237 (define_insn "*<code>qi_2_slp"
8238   [(set (reg FLAGS_REG)
8239         (compare (any_or:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8240                             (match_operand:QI 1 "general_operand" "qmn,qn"))
8241                  (const_int 0)))
8242    (set (strict_low_part (match_dup 0))
8243         (any_or:QI (match_dup 0) (match_dup 1)))]
8244   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8245    && ix86_match_ccmode (insn, CCNOmode)
8246    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8247   "<logic>{b}\t{%1, %0|%0, %1}"
8248   [(set_attr "type" "alu1")
8249    (set_attr "mode" "QI")])
8250
8251 (define_insn "*<code><mode>_3"
8252   [(set (reg FLAGS_REG)
8253         (compare (any_or:SWI
8254                   (match_operand:SWI 1 "nonimmediate_operand" "%0")
8255                   (match_operand:SWI 2 "<general_operand>" "<g>"))
8256                  (const_int 0)))
8257    (clobber (match_scratch:SWI 0 "=<r>"))]
8258   "ix86_match_ccmode (insn, CCNOmode)
8259    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8260   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8261   [(set_attr "type" "alu")
8262    (set_attr "mode" "<MODE>")])
8263
8264 (define_insn "*<code>qi_ext_0"
8265   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8266                          (const_int 8)
8267                          (const_int 8))
8268         (any_or:SI
8269           (zero_extract:SI
8270             (match_operand 1 "ext_register_operand" "0")
8271             (const_int 8)
8272             (const_int 8))
8273           (match_operand 2 "const_int_operand" "n")))
8274    (clobber (reg:CC FLAGS_REG))]
8275   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8276   "<logic>{b}\t{%2, %h0|%h0, %2}"
8277   [(set_attr "type" "alu")
8278    (set_attr "length_immediate" "1")
8279    (set_attr "modrm" "1")
8280    (set_attr "mode" "QI")])
8281
8282 (define_insn "*<code>qi_ext_1_rex64"
8283   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8284                          (const_int 8)
8285                          (const_int 8))
8286         (any_or:SI
8287           (zero_extract:SI
8288             (match_operand 1 "ext_register_operand" "0")
8289             (const_int 8)
8290             (const_int 8))
8291           (zero_extend:SI
8292             (match_operand 2 "ext_register_operand" "Q"))))
8293    (clobber (reg:CC FLAGS_REG))]
8294   "TARGET_64BIT
8295    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8296   "<logic>{b}\t{%2, %h0|%h0, %2}"
8297   [(set_attr "type" "alu")
8298    (set_attr "length_immediate" "0")
8299    (set_attr "mode" "QI")])
8300
8301 (define_insn "*<code>qi_ext_1"
8302   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8303                          (const_int 8)
8304                          (const_int 8))
8305         (any_or:SI
8306           (zero_extract:SI
8307             (match_operand 1 "ext_register_operand" "0")
8308             (const_int 8)
8309             (const_int 8))
8310           (zero_extend:SI
8311             (match_operand:QI 2 "general_operand" "Qm"))))
8312    (clobber (reg:CC FLAGS_REG))]
8313   "!TARGET_64BIT
8314    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8315   "<logic>{b}\t{%2, %h0|%h0, %2}"
8316   [(set_attr "type" "alu")
8317    (set_attr "length_immediate" "0")
8318    (set_attr "mode" "QI")])
8319
8320 (define_insn "*<code>qi_ext_2"
8321   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8322                          (const_int 8)
8323                          (const_int 8))
8324         (any_or:SI
8325           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8326                            (const_int 8)
8327                            (const_int 8))
8328           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8329                            (const_int 8)
8330                            (const_int 8))))
8331    (clobber (reg:CC FLAGS_REG))]
8332   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8333   "<logic>{b}\t{%h2, %h0|%h0, %h2}"
8334   [(set_attr "type" "alu")
8335    (set_attr "length_immediate" "0")
8336    (set_attr "mode" "QI")])
8337
8338 (define_split
8339   [(set (match_operand 0 "register_operand" "")
8340         (any_or (match_operand 1 "register_operand" "")
8341                 (match_operand 2 "const_int_operand" "")))
8342    (clobber (reg:CC FLAGS_REG))]
8343    "reload_completed
8344     && QI_REG_P (operands[0])
8345     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8346     && !(INTVAL (operands[2]) & ~(255 << 8))
8347     && GET_MODE (operands[0]) != QImode"
8348   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8349                    (any_or:SI (zero_extract:SI (match_dup 1)
8350                                                (const_int 8) (const_int 8))
8351                               (match_dup 2)))
8352               (clobber (reg:CC FLAGS_REG))])]
8353 {
8354   operands[0] = gen_lowpart (SImode, operands[0]);
8355   operands[1] = gen_lowpart (SImode, operands[1]);
8356   operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);
8357 })
8358
8359 ;; Since OR can be encoded with sign extended immediate, this is only
8360 ;; profitable when 7th bit is set.
8361 (define_split
8362   [(set (match_operand 0 "register_operand" "")
8363         (any_or (match_operand 1 "general_operand" "")
8364                 (match_operand 2 "const_int_operand" "")))
8365    (clobber (reg:CC FLAGS_REG))]
8366    "reload_completed
8367     && ANY_QI_REG_P (operands[0])
8368     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8369     && !(INTVAL (operands[2]) & ~255)
8370     && (INTVAL (operands[2]) & 128)
8371     && GET_MODE (operands[0]) != QImode"
8372   [(parallel [(set (strict_low_part (match_dup 0))
8373                    (any_or:QI (match_dup 1)
8374                               (match_dup 2)))
8375               (clobber (reg:CC FLAGS_REG))])]
8376 {
8377   operands[0] = gen_lowpart (QImode, operands[0]);
8378   operands[1] = gen_lowpart (QImode, operands[1]);
8379   operands[2] = gen_lowpart (QImode, operands[2]);
8380 })
8381
8382 (define_expand "xorqi_cc_ext_1"
8383   [(parallel [
8384      (set (reg:CCNO FLAGS_REG)
8385           (compare:CCNO
8386             (xor:SI
8387               (zero_extract:SI
8388                 (match_operand 1 "ext_register_operand" "")
8389                 (const_int 8)
8390                 (const_int 8))
8391               (match_operand:QI 2 "general_operand" ""))
8392             (const_int 0)))
8393      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
8394                            (const_int 8)
8395                            (const_int 8))
8396           (xor:SI
8397             (zero_extract:SI
8398              (match_dup 1)
8399              (const_int 8)
8400              (const_int 8))
8401             (match_dup 2)))])])
8402
8403 (define_insn "*xorqi_cc_ext_1_rex64"
8404   [(set (reg FLAGS_REG)
8405         (compare
8406           (xor:SI
8407             (zero_extract:SI
8408               (match_operand 1 "ext_register_operand" "0")
8409               (const_int 8)
8410               (const_int 8))
8411             (match_operand:QI 2 "nonmemory_operand" "Qn"))
8412           (const_int 0)))
8413    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8414                          (const_int 8)
8415                          (const_int 8))
8416         (xor:SI
8417           (zero_extract:SI
8418            (match_dup 1)
8419            (const_int 8)
8420            (const_int 8))
8421           (match_dup 2)))]
8422   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8423   "xor{b}\t{%2, %h0|%h0, %2}"
8424   [(set_attr "type" "alu")
8425    (set_attr "modrm" "1")
8426    (set_attr "mode" "QI")])
8427
8428 (define_insn "*xorqi_cc_ext_1"
8429   [(set (reg FLAGS_REG)
8430         (compare
8431           (xor:SI
8432             (zero_extract:SI
8433               (match_operand 1 "ext_register_operand" "0")
8434               (const_int 8)
8435               (const_int 8))
8436             (match_operand:QI 2 "general_operand" "qmn"))
8437           (const_int 0)))
8438    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
8439                          (const_int 8)
8440                          (const_int 8))
8441         (xor:SI
8442           (zero_extract:SI
8443            (match_dup 1)
8444            (const_int 8)
8445            (const_int 8))
8446           (match_dup 2)))]
8447   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8448   "xor{b}\t{%2, %h0|%h0, %2}"
8449   [(set_attr "type" "alu")
8450    (set_attr "modrm" "1")
8451    (set_attr "mode" "QI")])
8452 \f
8453 ;; Negation instructions
8454
8455 (define_expand "neg<mode>2"
8456   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
8457         (neg:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")))]
8458   ""
8459   "ix86_expand_unary_operator (NEG, <MODE>mode, operands); DONE;")
8460
8461 (define_insn_and_split "*neg<dwi>2_doubleword"
8462   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=ro")
8463         (neg:<DWI> (match_operand:<DWI> 1 "nonimmediate_operand" "0")))
8464    (clobber (reg:CC FLAGS_REG))]
8465   "ix86_unary_operator_ok (NEG, <DWI>mode, operands)"
8466   "#"
8467   "reload_completed"
8468   [(parallel
8469     [(set (reg:CCZ FLAGS_REG)
8470           (compare:CCZ (neg:DWIH (match_dup 1)) (const_int 0)))
8471      (set (match_dup 0) (neg:DWIH (match_dup 1)))])
8472    (parallel
8473     [(set (match_dup 2)
8474           (plus:DWIH (match_dup 3)
8475                      (plus:DWIH (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
8476                                 (const_int 0))))
8477      (clobber (reg:CC FLAGS_REG))])
8478    (parallel
8479     [(set (match_dup 2)
8480           (neg:DWIH (match_dup 2)))
8481      (clobber (reg:CC FLAGS_REG))])]
8482   "split_double_mode (<DWI>mode, &operands[0], 2, &operands[0], &operands[2]);")
8483
8484 (define_insn "*neg<mode>2_1"
8485   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8486         (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")))
8487    (clobber (reg:CC FLAGS_REG))]
8488   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8489   "neg{<imodesuffix>}\t%0"
8490   [(set_attr "type" "negnot")
8491    (set_attr "mode" "<MODE>")])
8492
8493 ;; Combine is quite creative about this pattern.
8494 (define_insn "*negsi2_1_zext"
8495   [(set (match_operand:DI 0 "register_operand" "=r")
8496         (lshiftrt:DI
8497           (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
8498                              (const_int 32)))
8499         (const_int 32)))
8500    (clobber (reg:CC FLAGS_REG))]
8501   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8502   "neg{l}\t%k0"
8503   [(set_attr "type" "negnot")
8504    (set_attr "mode" "SI")])
8505
8506 ;; The problem with neg is that it does not perform (compare x 0),
8507 ;; it really performs (compare 0 x), which leaves us with the zero
8508 ;; flag being the only useful item.
8509
8510 (define_insn "*neg<mode>2_cmpz"
8511   [(set (reg:CCZ FLAGS_REG)
8512         (compare:CCZ
8513           (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8514                    (const_int 0)))
8515    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8516         (neg:SWI (match_dup 1)))]
8517   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8518   "neg{<imodesuffix>}\t%0"
8519   [(set_attr "type" "negnot")
8520    (set_attr "mode" "<MODE>")])
8521
8522 (define_insn "*negsi2_cmpz_zext"
8523   [(set (reg:CCZ FLAGS_REG)
8524         (compare:CCZ
8525           (lshiftrt:DI
8526             (neg:DI (ashift:DI
8527                       (match_operand:DI 1 "register_operand" "0")
8528                       (const_int 32)))
8529             (const_int 32))
8530           (const_int 0)))
8531    (set (match_operand:DI 0 "register_operand" "=r")
8532         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
8533                                         (const_int 32)))
8534                      (const_int 32)))]
8535   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8536   "neg{l}\t%k0"
8537   [(set_attr "type" "negnot")
8538    (set_attr "mode" "SI")])
8539
8540 ;; Changing of sign for FP values is doable using integer unit too.
8541
8542 (define_expand "<code><mode>2"
8543   [(set (match_operand:X87MODEF 0 "register_operand" "")
8544         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
8545   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8546   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
8547
8548 (define_insn "*absneg<mode>2_mixed"
8549   [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
8550         (match_operator:MODEF 3 "absneg_operator"
8551           [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
8552    (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
8553    (clobber (reg:CC FLAGS_REG))]
8554   "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
8555   "#")
8556
8557 (define_insn "*absneg<mode>2_sse"
8558   [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
8559         (match_operator:MODEF 3 "absneg_operator"
8560           [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
8561    (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
8562    (clobber (reg:CC FLAGS_REG))]
8563   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
8564   "#")
8565
8566 (define_insn "*absneg<mode>2_i387"
8567   [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
8568         (match_operator:X87MODEF 3 "absneg_operator"
8569           [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
8570    (use (match_operand 2 "" ""))
8571    (clobber (reg:CC FLAGS_REG))]
8572   "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8573   "#")
8574
8575 (define_expand "<code>tf2"
8576   [(set (match_operand:TF 0 "register_operand" "")
8577         (absneg:TF (match_operand:TF 1 "register_operand" "")))]
8578   "TARGET_SSE2"
8579   "ix86_expand_fp_absneg_operator (<CODE>, TFmode, operands); DONE;")
8580
8581 (define_insn "*absnegtf2_sse"
8582   [(set (match_operand:TF 0 "register_operand" "=x,x")
8583         (match_operator:TF 3 "absneg_operator"
8584           [(match_operand:TF 1 "register_operand" "0,x")]))
8585    (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
8586    (clobber (reg:CC FLAGS_REG))]
8587   "TARGET_SSE2"
8588   "#")
8589
8590 ;; Splitters for fp abs and neg.
8591
8592 (define_split
8593   [(set (match_operand 0 "fp_register_operand" "")
8594         (match_operator 1 "absneg_operator" [(match_dup 0)]))
8595    (use (match_operand 2 "" ""))
8596    (clobber (reg:CC FLAGS_REG))]
8597   "reload_completed"
8598   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
8599
8600 (define_split
8601   [(set (match_operand 0 "register_operand" "")
8602         (match_operator 3 "absneg_operator"
8603           [(match_operand 1 "register_operand" "")]))
8604    (use (match_operand 2 "nonimmediate_operand" ""))
8605    (clobber (reg:CC FLAGS_REG))]
8606   "reload_completed && SSE_REG_P (operands[0])"
8607   [(set (match_dup 0) (match_dup 3))]
8608 {
8609   enum machine_mode mode = GET_MODE (operands[0]);
8610   enum machine_mode vmode = GET_MODE (operands[2]);
8611   rtx tmp;
8612
8613   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
8614   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
8615   if (operands_match_p (operands[0], operands[2]))
8616     {
8617       tmp = operands[1];
8618       operands[1] = operands[2];
8619       operands[2] = tmp;
8620     }
8621   if (GET_CODE (operands[3]) == ABS)
8622     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
8623   else
8624     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
8625   operands[3] = tmp;
8626 })
8627
8628 (define_split
8629   [(set (match_operand:SF 0 "register_operand" "")
8630         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
8631    (use (match_operand:V4SF 2 "" ""))
8632    (clobber (reg:CC FLAGS_REG))]
8633   "reload_completed"
8634   [(parallel [(set (match_dup 0) (match_dup 1))
8635               (clobber (reg:CC FLAGS_REG))])]
8636 {
8637   rtx tmp;
8638   operands[0] = gen_lowpart (SImode, operands[0]);
8639   if (GET_CODE (operands[1]) == ABS)
8640     {
8641       tmp = gen_int_mode (0x7fffffff, SImode);
8642       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8643     }
8644   else
8645     {
8646       tmp = gen_int_mode (0x80000000, SImode);
8647       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8648     }
8649   operands[1] = tmp;
8650 })
8651
8652 (define_split
8653   [(set (match_operand:DF 0 "register_operand" "")
8654         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
8655    (use (match_operand 2 "" ""))
8656    (clobber (reg:CC FLAGS_REG))]
8657   "reload_completed"
8658   [(parallel [(set (match_dup 0) (match_dup 1))
8659               (clobber (reg:CC FLAGS_REG))])]
8660 {
8661   rtx tmp;
8662   if (TARGET_64BIT)
8663     {
8664       tmp = gen_lowpart (DImode, operands[0]);
8665       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
8666       operands[0] = tmp;
8667
8668       if (GET_CODE (operands[1]) == ABS)
8669         tmp = const0_rtx;
8670       else
8671         tmp = gen_rtx_NOT (DImode, tmp);
8672     }
8673   else
8674     {
8675       operands[0] = gen_highpart (SImode, operands[0]);
8676       if (GET_CODE (operands[1]) == ABS)
8677         {
8678           tmp = gen_int_mode (0x7fffffff, SImode);
8679           tmp = gen_rtx_AND (SImode, operands[0], tmp);
8680         }
8681       else
8682         {
8683           tmp = gen_int_mode (0x80000000, SImode);
8684           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8685         }
8686     }
8687   operands[1] = tmp;
8688 })
8689
8690 (define_split
8691   [(set (match_operand:XF 0 "register_operand" "")
8692         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
8693    (use (match_operand 2 "" ""))
8694    (clobber (reg:CC FLAGS_REG))]
8695   "reload_completed"
8696   [(parallel [(set (match_dup 0) (match_dup 1))
8697               (clobber (reg:CC FLAGS_REG))])]
8698 {
8699   rtx tmp;
8700   operands[0] = gen_rtx_REG (SImode,
8701                              true_regnum (operands[0])
8702                              + (TARGET_64BIT ? 1 : 2));
8703   if (GET_CODE (operands[1]) == ABS)
8704     {
8705       tmp = GEN_INT (0x7fff);
8706       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8707     }
8708   else
8709     {
8710       tmp = GEN_INT (0x8000);
8711       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8712     }
8713   operands[1] = tmp;
8714 })
8715
8716 ;; Conditionalize these after reload. If they match before reload, we
8717 ;; lose the clobber and ability to use integer instructions.
8718
8719 (define_insn "*<code><mode>2_1"
8720   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
8721         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
8722   "TARGET_80387
8723    && (reload_completed
8724        || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
8725   "f<absneg_mnemonic>"
8726   [(set_attr "type" "fsgn")
8727    (set_attr "mode" "<MODE>")])
8728
8729 (define_insn "*<code>extendsfdf2"
8730   [(set (match_operand:DF 0 "register_operand" "=f")
8731         (absneg:DF (float_extend:DF
8732                      (match_operand:SF 1 "register_operand" "0"))))]
8733   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
8734   "f<absneg_mnemonic>"
8735   [(set_attr "type" "fsgn")
8736    (set_attr "mode" "DF")])
8737
8738 (define_insn "*<code>extendsfxf2"
8739   [(set (match_operand:XF 0 "register_operand" "=f")
8740         (absneg:XF (float_extend:XF
8741                      (match_operand:SF 1 "register_operand" "0"))))]
8742   "TARGET_80387"
8743   "f<absneg_mnemonic>"
8744   [(set_attr "type" "fsgn")
8745    (set_attr "mode" "XF")])
8746
8747 (define_insn "*<code>extenddfxf2"
8748   [(set (match_operand:XF 0 "register_operand" "=f")
8749         (absneg:XF (float_extend:XF
8750                      (match_operand:DF 1 "register_operand" "0"))))]
8751   "TARGET_80387"
8752   "f<absneg_mnemonic>"
8753   [(set_attr "type" "fsgn")
8754    (set_attr "mode" "XF")])
8755
8756 ;; Copysign instructions
8757
8758 (define_mode_iterator CSGNMODE [SF DF TF])
8759 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
8760
8761 (define_expand "copysign<mode>3"
8762   [(match_operand:CSGNMODE 0 "register_operand" "")
8763    (match_operand:CSGNMODE 1 "nonmemory_operand" "")
8764    (match_operand:CSGNMODE 2 "register_operand" "")]
8765   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8766    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8767   "ix86_expand_copysign (operands); DONE;")
8768
8769 (define_insn_and_split "copysign<mode>3_const"
8770   [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
8771         (unspec:CSGNMODE
8772           [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
8773            (match_operand:CSGNMODE 2 "register_operand" "0")
8774            (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
8775           UNSPEC_COPYSIGN))]
8776   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8777    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8778   "#"
8779   "&& reload_completed"
8780   [(const_int 0)]
8781   "ix86_split_copysign_const (operands); DONE;")
8782
8783 (define_insn "copysign<mode>3_var"
8784   [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
8785         (unspec:CSGNMODE
8786           [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
8787            (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
8788            (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
8789            (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
8790           UNSPEC_COPYSIGN))
8791    (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
8792   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8793    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8794   "#")
8795
8796 (define_split
8797   [(set (match_operand:CSGNMODE 0 "register_operand" "")
8798         (unspec:CSGNMODE
8799           [(match_operand:CSGNMODE 2 "register_operand" "")
8800            (match_operand:CSGNMODE 3 "register_operand" "")
8801            (match_operand:<CSGNVMODE> 4 "" "")
8802            (match_operand:<CSGNVMODE> 5 "" "")]
8803           UNSPEC_COPYSIGN))
8804    (clobber (match_scratch:<CSGNVMODE> 1 ""))]
8805   "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8806     || (TARGET_SSE2 && (<MODE>mode == TFmode)))
8807    && reload_completed"
8808   [(const_int 0)]
8809   "ix86_split_copysign_var (operands); DONE;")
8810 \f
8811 ;; One complement instructions
8812
8813 (define_expand "one_cmpl<mode>2"
8814   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8815         (not:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")))]
8816   ""
8817   "ix86_expand_unary_operator (NOT, <MODE>mode, operands); DONE;")
8818
8819 (define_insn "*one_cmpl<mode>2_1"
8820   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=rm")
8821         (not:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "0")))]
8822   "ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8823   "not{<imodesuffix>}\t%0"
8824   [(set_attr "type" "negnot")
8825    (set_attr "mode" "<MODE>")])
8826
8827 ;; %%% Potential partial reg stall on alternative 1.  What to do?
8828 (define_insn "*one_cmplqi2_1"
8829   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
8830         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
8831   "ix86_unary_operator_ok (NOT, QImode, operands)"
8832   "@
8833    not{b}\t%0
8834    not{l}\t%k0"
8835   [(set_attr "type" "negnot")
8836    (set_attr "mode" "QI,SI")])
8837
8838 ;; ??? Currently never generated - xor is used instead.
8839 (define_insn "*one_cmplsi2_1_zext"
8840   [(set (match_operand:DI 0 "register_operand" "=r")
8841         (zero_extend:DI
8842           (not:SI (match_operand:SI 1 "register_operand" "0"))))]
8843   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
8844   "not{l}\t%k0"
8845   [(set_attr "type" "negnot")
8846    (set_attr "mode" "SI")])
8847
8848 (define_insn "*one_cmpl<mode>2_2"
8849   [(set (reg FLAGS_REG)
8850         (compare (not:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8851                  (const_int 0)))
8852    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8853         (not:SWI (match_dup 1)))]
8854   "ix86_match_ccmode (insn, CCNOmode)
8855    && ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8856   "#"
8857   [(set_attr "type" "alu1")
8858    (set_attr "mode" "<MODE>")])
8859
8860 (define_split
8861   [(set (match_operand 0 "flags_reg_operand" "")
8862         (match_operator 2 "compare_operator"
8863           [(not:SWI (match_operand:SWI 3 "nonimmediate_operand" ""))
8864            (const_int 0)]))
8865    (set (match_operand:SWI 1 "nonimmediate_operand" "")
8866         (not:SWI (match_dup 3)))]
8867   "ix86_match_ccmode (insn, CCNOmode)"
8868   [(parallel [(set (match_dup 0)
8869                    (match_op_dup 2 [(xor:SWI (match_dup 3) (const_int -1))
8870                                     (const_int 0)]))
8871               (set (match_dup 1)
8872                    (xor:SWI (match_dup 3) (const_int -1)))])])
8873
8874 ;; ??? Currently never generated - xor is used instead.
8875 (define_insn "*one_cmplsi2_2_zext"
8876   [(set (reg FLAGS_REG)
8877         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
8878                  (const_int 0)))
8879    (set (match_operand:DI 0 "register_operand" "=r")
8880         (zero_extend:DI (not:SI (match_dup 1))))]
8881   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8882    && ix86_unary_operator_ok (NOT, SImode, operands)"
8883   "#"
8884   [(set_attr "type" "alu1")
8885    (set_attr "mode" "SI")])
8886
8887 (define_split
8888   [(set (match_operand 0 "flags_reg_operand" "")
8889         (match_operator 2 "compare_operator"
8890           [(not:SI (match_operand:SI 3 "register_operand" ""))
8891            (const_int 0)]))
8892    (set (match_operand:DI 1 "register_operand" "")
8893         (zero_extend:DI (not:SI (match_dup 3))))]
8894   "ix86_match_ccmode (insn, CCNOmode)"
8895   [(parallel [(set (match_dup 0)
8896                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
8897                                     (const_int 0)]))
8898               (set (match_dup 1)
8899                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])])
8900 \f
8901 ;; Shift instructions
8902
8903 ;; DImode shifts are implemented using the i386 "shift double" opcode,
8904 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
8905 ;; is variable, then the count is in %cl and the "imm" operand is dropped
8906 ;; from the assembler input.
8907 ;;
8908 ;; This instruction shifts the target reg/mem as usual, but instead of
8909 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
8910 ;; is a left shift double, bits are taken from the high order bits of
8911 ;; reg, else if the insn is a shift right double, bits are taken from the
8912 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
8913 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
8914 ;;
8915 ;; Since sh[lr]d does not change the `reg' operand, that is done
8916 ;; separately, making all shifts emit pairs of shift double and normal
8917 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
8918 ;; support a 63 bit shift, each shift where the count is in a reg expands
8919 ;; to a pair of shifts, a branch, a shift by 32 and a label.
8920 ;;
8921 ;; If the shift count is a constant, we need never emit more than one
8922 ;; shift pair, instead using moves and sign extension for counts greater
8923 ;; than 31.
8924
8925 (define_expand "ashl<mode>3"
8926   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
8927         (ashift:SDWIM (match_operand:SDWIM 1 "<ashl_input_operand>" "")
8928                       (match_operand:QI 2 "nonmemory_operand" "")))]
8929   ""
8930   "ix86_expand_binary_operator (ASHIFT, <MODE>mode, operands); DONE;")
8931
8932 (define_insn "*ashl<mode>3_doubleword"
8933   [(set (match_operand:DWI 0 "register_operand" "=&r,r")
8934         (ashift:DWI (match_operand:DWI 1 "reg_or_pm1_operand" "n,0")
8935                     (match_operand:QI 2 "nonmemory_operand" "<S>c,<S>c")))
8936    (clobber (reg:CC FLAGS_REG))]
8937   ""
8938   "#"
8939   [(set_attr "type" "multi")])
8940
8941 (define_split
8942   [(set (match_operand:DWI 0 "register_operand" "")
8943         (ashift:DWI (match_operand:DWI 1 "nonmemory_operand" "")
8944                     (match_operand:QI 2 "nonmemory_operand" "")))
8945    (clobber (reg:CC FLAGS_REG))]
8946   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
8947   [(const_int 0)]
8948   "ix86_split_ashl (operands, NULL_RTX, <MODE>mode); DONE;")
8949
8950 ;; By default we don't ask for a scratch register, because when DWImode
8951 ;; values are manipulated, registers are already at a premium.  But if
8952 ;; we have one handy, we won't turn it away.
8953
8954 (define_peephole2
8955   [(match_scratch:DWIH 3 "r")
8956    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
8957                    (ashift:<DWI>
8958                      (match_operand:<DWI> 1 "nonmemory_operand" "")
8959                      (match_operand:QI 2 "nonmemory_operand" "")))
8960               (clobber (reg:CC FLAGS_REG))])
8961    (match_dup 3)]
8962   "TARGET_CMOVE"
8963   [(const_int 0)]
8964   "ix86_split_ashl (operands, operands[3], <DWI>mode); DONE;")
8965
8966 (define_insn "x86_64_shld"
8967   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
8968         (ior:DI (ashift:DI (match_dup 0)
8969                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
8970                 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
8971                   (minus:QI (const_int 64) (match_dup 2)))))
8972    (clobber (reg:CC FLAGS_REG))]
8973   "TARGET_64BIT"
8974   "shld{q}\t{%s2%1, %0|%0, %1, %2}"
8975   [(set_attr "type" "ishift")
8976    (set_attr "prefix_0f" "1")
8977    (set_attr "mode" "DI")
8978    (set_attr "athlon_decode" "vector")
8979    (set_attr "amdfam10_decode" "vector")
8980    (set_attr "bdver1_decode" "vector")])
8981
8982 (define_insn "x86_shld"
8983   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
8984         (ior:SI (ashift:SI (match_dup 0)
8985                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
8986                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
8987                   (minus:QI (const_int 32) (match_dup 2)))))
8988    (clobber (reg:CC FLAGS_REG))]
8989   ""
8990   "shld{l}\t{%s2%1, %0|%0, %1, %2}"
8991   [(set_attr "type" "ishift")
8992    (set_attr "prefix_0f" "1")
8993    (set_attr "mode" "SI")
8994    (set_attr "pent_pair" "np")
8995    (set_attr "athlon_decode" "vector")
8996    (set_attr "amdfam10_decode" "vector")
8997    (set_attr "bdver1_decode" "vector")])
8998
8999 (define_expand "x86_shift<mode>_adj_1"
9000   [(set (reg:CCZ FLAGS_REG)
9001         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
9002                              (match_dup 4))
9003                      (const_int 0)))
9004    (set (match_operand:SWI48 0 "register_operand" "")
9005         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
9006                             (match_operand:SWI48 1 "register_operand" "")
9007                             (match_dup 0)))
9008    (set (match_dup 1)
9009         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
9010                             (match_operand:SWI48 3 "register_operand" "")
9011                             (match_dup 1)))]
9012   "TARGET_CMOVE"
9013   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
9014
9015 (define_expand "x86_shift<mode>_adj_2"
9016   [(use (match_operand:SWI48 0 "register_operand" ""))
9017    (use (match_operand:SWI48 1 "register_operand" ""))
9018    (use (match_operand:QI 2 "register_operand" ""))]
9019   ""
9020 {
9021   rtx label = gen_label_rtx ();
9022   rtx tmp;
9023
9024   emit_insn (gen_testqi_ccz_1 (operands[2],
9025                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9026
9027   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9028   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9029   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9030                               gen_rtx_LABEL_REF (VOIDmode, label),
9031                               pc_rtx);
9032   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9033   JUMP_LABEL (tmp) = label;
9034
9035   emit_move_insn (operands[0], operands[1]);
9036   ix86_expand_clear (operands[1]);
9037
9038   emit_label (label);
9039   LABEL_NUSES (label) = 1;
9040
9041   DONE;
9042 })
9043
9044 ;; Avoid useless masking of count operand.
9045 (define_insn_and_split "*ashl<mode>3_mask"
9046   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9047         (ashift:SWI48
9048           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9049           (subreg:QI
9050             (and:SI
9051               (match_operand:SI 2 "nonimmediate_operand" "c")
9052               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9053    (clobber (reg:CC FLAGS_REG))]
9054   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)
9055    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9056       == GET_MODE_BITSIZE (<MODE>mode)-1"
9057   "#"
9058   "&& 1"
9059   [(parallel [(set (match_dup 0)
9060                    (ashift:SWI48 (match_dup 1) (match_dup 2)))
9061               (clobber (reg:CC FLAGS_REG))])]
9062 {
9063   if (can_create_pseudo_p ())
9064     operands [2] = force_reg (SImode, operands[2]);
9065
9066   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9067 }
9068   [(set_attr "type" "ishift")
9069    (set_attr "mode" "<MODE>")])
9070
9071 (define_insn "*bmi2_ashl<mode>3_1"
9072   [(set (match_operand:SWI48 0 "register_operand" "=r")
9073         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9074                       (match_operand:SWI48 2 "register_operand" "r")))]
9075   "TARGET_BMI2"
9076   "shlx\t{%2, %1, %0|%0, %1, %2}"
9077   [(set_attr "type" "ishiftx")
9078    (set_attr "mode" "<MODE>")])
9079
9080 (define_insn "*ashl<mode>3_1"
9081   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r,r")
9082         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,l,rm")
9083                       (match_operand:QI 2 "nonmemory_operand" "c<S>,M,r")))
9084    (clobber (reg:CC FLAGS_REG))]
9085   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9086 {
9087   switch (get_attr_type (insn))
9088     {
9089     case TYPE_LEA:
9090     case TYPE_ISHIFTX:
9091       return "#";
9092
9093     case TYPE_ALU:
9094       gcc_assert (operands[2] == const1_rtx);
9095       gcc_assert (rtx_equal_p (operands[0], operands[1]));
9096       return "add{<imodesuffix>}\t%0, %0";
9097
9098     default:
9099       if (operands[2] == const1_rtx
9100           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9101         return "sal{<imodesuffix>}\t%0";
9102       else
9103         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9104     }
9105 }
9106   [(set_attr "isa" "*,*,bmi2")
9107    (set (attr "type")
9108      (cond [(eq_attr "alternative" "1")
9109               (const_string "lea")
9110             (eq_attr "alternative" "2")
9111               (const_string "ishiftx")
9112             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9113                       (match_operand 0 "register_operand" ""))
9114                  (match_operand 2 "const1_operand" ""))
9115               (const_string "alu")
9116            ]
9117            (const_string "ishift")))
9118    (set (attr "length_immediate")
9119      (if_then_else
9120        (ior (eq_attr "type" "alu")
9121             (and (eq_attr "type" "ishift")
9122                  (and (match_operand 2 "const1_operand" "")
9123                       (ior (match_test "TARGET_SHIFT1")
9124                            (match_test "optimize_function_for_size_p (cfun)")))))
9125        (const_string "0")
9126        (const_string "*")))
9127    (set_attr "mode" "<MODE>")])
9128
9129 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9130 (define_split
9131   [(set (match_operand:SWI48 0 "register_operand" "")
9132         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9133                       (match_operand:QI 2 "register_operand" "")))
9134    (clobber (reg:CC FLAGS_REG))]
9135   "TARGET_BMI2 && reload_completed"
9136   [(set (match_dup 0)
9137         (ashift:SWI48 (match_dup 1) (match_dup 2)))]
9138   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9139
9140 (define_insn "*bmi2_ashlsi3_1_zext"
9141   [(set (match_operand:DI 0 "register_operand" "=r")
9142         (zero_extend:DI
9143           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9144                      (match_operand:SI 2 "register_operand" "r"))))]
9145   "TARGET_64BIT && TARGET_BMI2"
9146   "shlx\t{%2, %1, %k0|%k0, %1, %2}"
9147   [(set_attr "type" "ishiftx")
9148    (set_attr "mode" "SI")])
9149
9150 (define_insn "*ashlsi3_1_zext"
9151   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
9152         (zero_extend:DI
9153           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l,rm")
9154                      (match_operand:QI 2 "nonmemory_operand" "cI,M,r"))))
9155    (clobber (reg:CC FLAGS_REG))]
9156   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9157 {
9158   switch (get_attr_type (insn))
9159     {
9160     case TYPE_LEA:
9161     case TYPE_ISHIFTX:
9162       return "#";
9163
9164     case TYPE_ALU:
9165       gcc_assert (operands[2] == const1_rtx);
9166       return "add{l}\t%k0, %k0";
9167
9168     default:
9169       if (operands[2] == const1_rtx
9170           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9171         return "sal{l}\t%k0";
9172       else
9173         return "sal{l}\t{%2, %k0|%k0, %2}";
9174     }
9175 }
9176   [(set_attr "isa" "*,*,bmi2")
9177    (set (attr "type")
9178      (cond [(eq_attr "alternative" "1")
9179               (const_string "lea")
9180             (eq_attr "alternative" "2")
9181               (const_string "ishiftx")
9182             (and (match_test "TARGET_DOUBLE_WITH_ADD")
9183                  (match_operand 2 "const1_operand" ""))
9184               (const_string "alu")
9185            ]
9186            (const_string "ishift")))
9187    (set (attr "length_immediate")
9188      (if_then_else
9189        (ior (eq_attr "type" "alu")
9190             (and (eq_attr "type" "ishift")
9191                  (and (match_operand 2 "const1_operand" "")
9192                       (ior (match_test "TARGET_SHIFT1")
9193                            (match_test "optimize_function_for_size_p (cfun)")))))
9194        (const_string "0")
9195        (const_string "*")))
9196    (set_attr "mode" "SI")])
9197
9198 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9199 (define_split
9200   [(set (match_operand:DI 0 "register_operand" "")
9201         (zero_extend:DI
9202           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
9203                      (match_operand:QI 2 "register_operand" ""))))
9204    (clobber (reg:CC FLAGS_REG))]
9205   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9206   [(set (match_dup 0)
9207         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9208   "operands[2] = gen_lowpart (SImode, operands[2]);")
9209
9210 (define_insn "*ashlhi3_1"
9211   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,Yp")
9212         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
9213                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
9214    (clobber (reg:CC FLAGS_REG))]
9215   "ix86_binary_operator_ok (ASHIFT, HImode, operands)"
9216 {
9217   switch (get_attr_type (insn))
9218     {
9219     case TYPE_LEA:
9220       return "#";
9221
9222     case TYPE_ALU:
9223       gcc_assert (operands[2] == const1_rtx);
9224       return "add{w}\t%0, %0";
9225
9226     default:
9227       if (operands[2] == const1_rtx
9228           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9229         return "sal{w}\t%0";
9230       else
9231         return "sal{w}\t{%2, %0|%0, %2}";
9232     }
9233 }
9234   [(set (attr "type")
9235      (cond [(eq_attr "alternative" "1")
9236               (const_string "lea")
9237             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9238                       (match_operand 0 "register_operand" ""))
9239                  (match_operand 2 "const1_operand" ""))
9240               (const_string "alu")
9241            ]
9242            (const_string "ishift")))
9243    (set (attr "length_immediate")
9244      (if_then_else
9245        (ior (eq_attr "type" "alu")
9246             (and (eq_attr "type" "ishift")
9247                  (and (match_operand 2 "const1_operand" "")
9248                       (ior (match_test "TARGET_SHIFT1")
9249                            (match_test "optimize_function_for_size_p (cfun)")))))
9250        (const_string "0")
9251        (const_string "*")))
9252    (set_attr "mode" "HI,SI")])
9253
9254 ;; %%% Potential partial reg stall on alternative 1.  What to do?
9255 (define_insn "*ashlqi3_1"
9256   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,Yp")
9257         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
9258                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
9259    (clobber (reg:CC FLAGS_REG))]
9260   "ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9261 {
9262   switch (get_attr_type (insn))
9263     {
9264     case TYPE_LEA:
9265       return "#";
9266
9267     case TYPE_ALU:
9268       gcc_assert (operands[2] == const1_rtx);
9269       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
9270         return "add{l}\t%k0, %k0";
9271       else
9272         return "add{b}\t%0, %0";
9273
9274     default:
9275       if (operands[2] == const1_rtx
9276           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9277         {
9278           if (get_attr_mode (insn) == MODE_SI)
9279             return "sal{l}\t%k0";
9280           else
9281             return "sal{b}\t%0";
9282         }
9283       else
9284         {
9285           if (get_attr_mode (insn) == MODE_SI)
9286             return "sal{l}\t{%2, %k0|%k0, %2}";
9287           else
9288             return "sal{b}\t{%2, %0|%0, %2}";
9289         }
9290     }
9291 }
9292   [(set (attr "type")
9293      (cond [(eq_attr "alternative" "2")
9294               (const_string "lea")
9295             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9296                       (match_operand 0 "register_operand" ""))
9297                  (match_operand 2 "const1_operand" ""))
9298               (const_string "alu")
9299            ]
9300            (const_string "ishift")))
9301    (set (attr "length_immediate")
9302      (if_then_else
9303        (ior (eq_attr "type" "alu")
9304             (and (eq_attr "type" "ishift")
9305                  (and (match_operand 2 "const1_operand" "")
9306                       (ior (match_test "TARGET_SHIFT1")
9307                            (match_test "optimize_function_for_size_p (cfun)")))))
9308        (const_string "0")
9309        (const_string "*")))
9310    (set_attr "mode" "QI,SI,SI")])
9311
9312 (define_insn "*ashlqi3_1_slp"
9313   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9314         (ashift:QI (match_dup 0)
9315                    (match_operand:QI 1 "nonmemory_operand" "cI")))
9316    (clobber (reg:CC FLAGS_REG))]
9317   "(optimize_function_for_size_p (cfun)
9318     || !TARGET_PARTIAL_FLAG_REG_STALL
9319     || (operands[1] == const1_rtx
9320         && (TARGET_SHIFT1
9321             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))"
9322 {
9323   switch (get_attr_type (insn))
9324     {
9325     case TYPE_ALU:
9326       gcc_assert (operands[1] == const1_rtx);
9327       return "add{b}\t%0, %0";
9328
9329     default:
9330       if (operands[1] == const1_rtx
9331           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9332         return "sal{b}\t%0";
9333       else
9334         return "sal{b}\t{%1, %0|%0, %1}";
9335     }
9336 }
9337   [(set (attr "type")
9338      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9339                       (match_operand 0 "register_operand" ""))
9340                  (match_operand 1 "const1_operand" ""))
9341               (const_string "alu")
9342            ]
9343            (const_string "ishift1")))
9344    (set (attr "length_immediate")
9345      (if_then_else
9346        (ior (eq_attr "type" "alu")
9347             (and (eq_attr "type" "ishift1")
9348                  (and (match_operand 1 "const1_operand" "")
9349                       (ior (match_test "TARGET_SHIFT1")
9350                            (match_test "optimize_function_for_size_p (cfun)")))))
9351        (const_string "0")
9352        (const_string "*")))
9353    (set_attr "mode" "QI")])
9354
9355 ;; Convert ashift to the lea pattern to avoid flags dependency.
9356 (define_split
9357   [(set (match_operand 0 "register_operand" "")
9358         (ashift (match_operand 1 "index_register_operand" "")
9359                 (match_operand:QI 2 "const_int_operand" "")))
9360    (clobber (reg:CC FLAGS_REG))]
9361   "GET_MODE (operands[0]) == GET_MODE (operands[1])
9362    && reload_completed
9363    && true_regnum (operands[0]) != true_regnum (operands[1])"
9364   [(const_int 0)]
9365 {
9366   enum machine_mode mode = GET_MODE (operands[0]);
9367   rtx pat;
9368
9369   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
9370     { 
9371       mode = SImode; 
9372       operands[0] = gen_lowpart (mode, operands[0]);
9373       operands[1] = gen_lowpart (mode, operands[1]);
9374     }
9375
9376   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), mode);
9377
9378   pat = gen_rtx_MULT (mode, operands[1], operands[2]);
9379
9380   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
9381   DONE;
9382 })
9383
9384 ;; Convert ashift to the lea pattern to avoid flags dependency.
9385 (define_split
9386   [(set (match_operand:DI 0 "register_operand" "")
9387         (zero_extend:DI
9388           (ashift:SI (match_operand:SI 1 "index_register_operand" "")
9389                      (match_operand:QI 2 "const_int_operand" ""))))
9390    (clobber (reg:CC FLAGS_REG))]
9391   "TARGET_64BIT && reload_completed
9392    && true_regnum (operands[0]) != true_regnum (operands[1])"
9393   [(set (match_dup 0)
9394         (zero_extend:DI (subreg:SI (mult:DI (match_dup 1) (match_dup 2)) 0)))]
9395 {
9396   operands[1] = gen_lowpart (DImode, operands[1]);
9397   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);
9398 })
9399
9400 ;; This pattern can't accept a variable shift count, since shifts by
9401 ;; zero don't affect the flags.  We assume that shifts by constant
9402 ;; zero are optimized away.
9403 (define_insn "*ashl<mode>3_cmp"
9404   [(set (reg FLAGS_REG)
9405         (compare
9406           (ashift:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")
9407                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9408           (const_int 0)))
9409    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9410         (ashift:SWI (match_dup 1) (match_dup 2)))]
9411   "(optimize_function_for_size_p (cfun)
9412     || !TARGET_PARTIAL_FLAG_REG_STALL
9413     || (operands[2] == const1_rtx
9414         && (TARGET_SHIFT1
9415             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
9416    && ix86_match_ccmode (insn, CCGOCmode)
9417    && ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9418 {
9419   switch (get_attr_type (insn))
9420     {
9421     case TYPE_ALU:
9422       gcc_assert (operands[2] == const1_rtx);
9423       return "add{<imodesuffix>}\t%0, %0";
9424
9425     default:
9426       if (operands[2] == const1_rtx
9427           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9428         return "sal{<imodesuffix>}\t%0";
9429       else
9430         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9431     }
9432 }
9433   [(set (attr "type")
9434      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9435                       (match_operand 0 "register_operand" ""))
9436                  (match_operand 2 "const1_operand" ""))
9437               (const_string "alu")
9438            ]
9439            (const_string "ishift")))
9440    (set (attr "length_immediate")
9441      (if_then_else
9442        (ior (eq_attr "type" "alu")
9443             (and (eq_attr "type" "ishift")
9444                  (and (match_operand 2 "const1_operand" "")
9445                       (ior (match_test "TARGET_SHIFT1")
9446                            (match_test "optimize_function_for_size_p (cfun)")))))
9447        (const_string "0")
9448        (const_string "*")))
9449    (set_attr "mode" "<MODE>")])
9450
9451 (define_insn "*ashlsi3_cmp_zext"
9452   [(set (reg FLAGS_REG)
9453         (compare
9454           (ashift:SI (match_operand:SI 1 "register_operand" "0")
9455                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
9456           (const_int 0)))
9457    (set (match_operand:DI 0 "register_operand" "=r")
9458         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9459   "TARGET_64BIT
9460    && (optimize_function_for_size_p (cfun)
9461        || !TARGET_PARTIAL_FLAG_REG_STALL
9462        || (operands[2] == const1_rtx
9463            && (TARGET_SHIFT1
9464                || TARGET_DOUBLE_WITH_ADD)))
9465    && ix86_match_ccmode (insn, CCGOCmode)
9466    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9467 {
9468   switch (get_attr_type (insn))
9469     {
9470     case TYPE_ALU:
9471       gcc_assert (operands[2] == const1_rtx);
9472       return "add{l}\t%k0, %k0";
9473
9474     default:
9475       if (operands[2] == const1_rtx
9476           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9477         return "sal{l}\t%k0";
9478       else
9479         return "sal{l}\t{%2, %k0|%k0, %2}";
9480     }
9481 }
9482   [(set (attr "type")
9483      (cond [(and (match_test "TARGET_DOUBLE_WITH_ADD")
9484                  (match_operand 2 "const1_operand" ""))
9485               (const_string "alu")
9486            ]
9487            (const_string "ishift")))
9488    (set (attr "length_immediate")
9489      (if_then_else
9490        (ior (eq_attr "type" "alu")
9491             (and (eq_attr "type" "ishift")
9492                  (and (match_operand 2 "const1_operand" "")
9493                       (ior (match_test "TARGET_SHIFT1")
9494                            (match_test "optimize_function_for_size_p (cfun)")))))
9495        (const_string "0")
9496        (const_string "*")))
9497    (set_attr "mode" "SI")])
9498
9499 (define_insn "*ashl<mode>3_cconly"
9500   [(set (reg FLAGS_REG)
9501         (compare
9502           (ashift:SWI (match_operand:SWI 1 "register_operand" "0")
9503                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9504           (const_int 0)))
9505    (clobber (match_scratch:SWI 0 "=<r>"))]
9506   "(optimize_function_for_size_p (cfun)
9507     || !TARGET_PARTIAL_FLAG_REG_STALL
9508     || (operands[2] == const1_rtx
9509         && (TARGET_SHIFT1
9510             || TARGET_DOUBLE_WITH_ADD)))
9511    && ix86_match_ccmode (insn, CCGOCmode)"
9512 {
9513   switch (get_attr_type (insn))
9514     {
9515     case TYPE_ALU:
9516       gcc_assert (operands[2] == const1_rtx);
9517       return "add{<imodesuffix>}\t%0, %0";
9518
9519     default:
9520       if (operands[2] == const1_rtx
9521           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9522         return "sal{<imodesuffix>}\t%0";
9523       else
9524         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9525     }
9526 }
9527   [(set (attr "type")
9528      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9529                       (match_operand 0 "register_operand" ""))
9530                  (match_operand 2 "const1_operand" ""))
9531               (const_string "alu")
9532            ]
9533            (const_string "ishift")))
9534    (set (attr "length_immediate")
9535      (if_then_else
9536        (ior (eq_attr "type" "alu")
9537             (and (eq_attr "type" "ishift")
9538                  (and (match_operand 2 "const1_operand" "")
9539                       (ior (match_test "TARGET_SHIFT1")
9540                            (match_test "optimize_function_for_size_p (cfun)")))))
9541        (const_string "0")
9542        (const_string "*")))
9543    (set_attr "mode" "<MODE>")])
9544
9545 ;; See comment above `ashl<mode>3' about how this works.
9546
9547 (define_expand "<shift_insn><mode>3"
9548   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
9549         (any_shiftrt:SDWIM (match_operand:SDWIM 1 "<shift_operand>" "")
9550                            (match_operand:QI 2 "nonmemory_operand" "")))]
9551   ""
9552   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
9553
9554 ;; Avoid useless masking of count operand.
9555 (define_insn_and_split "*<shift_insn><mode>3_mask"
9556   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9557         (any_shiftrt:SWI48
9558           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9559           (subreg:QI
9560             (and:SI
9561               (match_operand:SI 2 "nonimmediate_operand" "c")
9562               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9563    (clobber (reg:CC FLAGS_REG))]
9564   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
9565    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9566       == GET_MODE_BITSIZE (<MODE>mode)-1"
9567   "#"
9568   "&& 1"
9569   [(parallel [(set (match_dup 0)
9570                    (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))
9571               (clobber (reg:CC FLAGS_REG))])]
9572 {
9573   if (can_create_pseudo_p ())
9574     operands [2] = force_reg (SImode, operands[2]);
9575
9576   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9577 }
9578   [(set_attr "type" "ishift")
9579    (set_attr "mode" "<MODE>")])
9580
9581 (define_insn_and_split "*<shift_insn><mode>3_doubleword"
9582   [(set (match_operand:DWI 0 "register_operand" "=r")
9583         (any_shiftrt:DWI (match_operand:DWI 1 "register_operand" "0")
9584                          (match_operand:QI 2 "nonmemory_operand" "<S>c")))
9585    (clobber (reg:CC FLAGS_REG))]
9586   ""
9587   "#"
9588   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
9589   [(const_int 0)]
9590   "ix86_split_<shift_insn> (operands, NULL_RTX, <MODE>mode); DONE;"
9591   [(set_attr "type" "multi")])
9592
9593 ;; By default we don't ask for a scratch register, because when DWImode
9594 ;; values are manipulated, registers are already at a premium.  But if
9595 ;; we have one handy, we won't turn it away.
9596
9597 (define_peephole2
9598   [(match_scratch:DWIH 3 "r")
9599    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
9600                    (any_shiftrt:<DWI>
9601                      (match_operand:<DWI> 1 "register_operand" "")
9602                      (match_operand:QI 2 "nonmemory_operand" "")))
9603               (clobber (reg:CC FLAGS_REG))])
9604    (match_dup 3)]
9605   "TARGET_CMOVE"
9606   [(const_int 0)]
9607   "ix86_split_<shift_insn> (operands, operands[3], <DWI>mode); DONE;")
9608
9609 (define_insn "x86_64_shrd"
9610   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
9611         (ior:DI (ashiftrt:DI (match_dup 0)
9612                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
9613                 (ashift:DI (match_operand:DI 1 "register_operand" "r")
9614                   (minus:QI (const_int 64) (match_dup 2)))))
9615    (clobber (reg:CC FLAGS_REG))]
9616   "TARGET_64BIT"
9617   "shrd{q}\t{%s2%1, %0|%0, %1, %2}"
9618   [(set_attr "type" "ishift")
9619    (set_attr "prefix_0f" "1")
9620    (set_attr "mode" "DI")
9621    (set_attr "athlon_decode" "vector")
9622    (set_attr "amdfam10_decode" "vector")
9623    (set_attr "bdver1_decode" "vector")])
9624
9625 (define_insn "x86_shrd"
9626   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
9627         (ior:SI (ashiftrt:SI (match_dup 0)
9628                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
9629                 (ashift:SI (match_operand:SI 1 "register_operand" "r")
9630                   (minus:QI (const_int 32) (match_dup 2)))))
9631    (clobber (reg:CC FLAGS_REG))]
9632   ""
9633   "shrd{l}\t{%s2%1, %0|%0, %1, %2}"
9634   [(set_attr "type" "ishift")
9635    (set_attr "prefix_0f" "1")
9636    (set_attr "mode" "SI")
9637    (set_attr "pent_pair" "np")
9638    (set_attr "athlon_decode" "vector")
9639    (set_attr "amdfam10_decode" "vector")
9640    (set_attr "bdver1_decode" "vector")])
9641
9642 (define_insn "ashrdi3_cvt"
9643   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
9644         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
9645                      (match_operand:QI 2 "const_int_operand" "")))
9646    (clobber (reg:CC FLAGS_REG))]
9647   "TARGET_64BIT && INTVAL (operands[2]) == 63
9648    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9649    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
9650   "@
9651    {cqto|cqo}
9652    sar{q}\t{%2, %0|%0, %2}"
9653   [(set_attr "type" "imovx,ishift")
9654    (set_attr "prefix_0f" "0,*")
9655    (set_attr "length_immediate" "0,*")
9656    (set_attr "modrm" "0,1")
9657    (set_attr "mode" "DI")])
9658
9659 (define_insn "ashrsi3_cvt"
9660   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
9661         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
9662                      (match_operand:QI 2 "const_int_operand" "")))
9663    (clobber (reg:CC FLAGS_REG))]
9664   "INTVAL (operands[2]) == 31
9665    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9666    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9667   "@
9668    {cltd|cdq}
9669    sar{l}\t{%2, %0|%0, %2}"
9670   [(set_attr "type" "imovx,ishift")
9671    (set_attr "prefix_0f" "0,*")
9672    (set_attr "length_immediate" "0,*")
9673    (set_attr "modrm" "0,1")
9674    (set_attr "mode" "SI")])
9675
9676 (define_insn "*ashrsi3_cvt_zext"
9677   [(set (match_operand:DI 0 "register_operand" "=*d,r")
9678         (zero_extend:DI
9679           (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
9680                        (match_operand:QI 2 "const_int_operand" ""))))
9681    (clobber (reg:CC FLAGS_REG))]
9682   "TARGET_64BIT && INTVAL (operands[2]) == 31
9683    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9684    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9685   "@
9686    {cltd|cdq}
9687    sar{l}\t{%2, %k0|%k0, %2}"
9688   [(set_attr "type" "imovx,ishift")
9689    (set_attr "prefix_0f" "0,*")
9690    (set_attr "length_immediate" "0,*")
9691    (set_attr "modrm" "0,1")
9692    (set_attr "mode" "SI")])
9693
9694 (define_expand "x86_shift<mode>_adj_3"
9695   [(use (match_operand:SWI48 0 "register_operand" ""))
9696    (use (match_operand:SWI48 1 "register_operand" ""))
9697    (use (match_operand:QI 2 "register_operand" ""))]
9698   ""
9699 {
9700   rtx label = gen_label_rtx ();
9701   rtx tmp;
9702
9703   emit_insn (gen_testqi_ccz_1 (operands[2],
9704                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9705
9706   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9707   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9708   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9709                               gen_rtx_LABEL_REF (VOIDmode, label),
9710                               pc_rtx);
9711   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9712   JUMP_LABEL (tmp) = label;
9713
9714   emit_move_insn (operands[0], operands[1]);
9715   emit_insn (gen_ashr<mode>3_cvt (operands[1], operands[1],
9716                                   GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1)));
9717   emit_label (label);
9718   LABEL_NUSES (label) = 1;
9719
9720   DONE;
9721 })
9722
9723 (define_insn "*bmi2_<shift_insn><mode>3_1"
9724   [(set (match_operand:SWI48 0 "register_operand" "=r")
9725         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9726                            (match_operand:SWI48 2 "register_operand" "r")))]
9727   "TARGET_BMI2"
9728   "<shift>x\t{%2, %1, %0|%0, %1, %2}"
9729   [(set_attr "type" "ishiftx")
9730    (set_attr "mode" "<MODE>")])
9731
9732 (define_insn "*<shift_insn><mode>3_1"
9733   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
9734         (any_shiftrt:SWI48
9735           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
9736           (match_operand:QI 2 "nonmemory_operand" "c<S>,r")))
9737    (clobber (reg:CC FLAGS_REG))]
9738   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9739 {
9740   switch (get_attr_type (insn))
9741     {
9742     case TYPE_ISHIFTX:
9743       return "#";
9744
9745     default:
9746       if (operands[2] == const1_rtx
9747           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9748         return "<shift>{<imodesuffix>}\t%0";
9749       else
9750         return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9751     }
9752 }
9753   [(set_attr "isa" "*,bmi2")
9754    (set_attr "type" "ishift,ishiftx")
9755    (set (attr "length_immediate")
9756      (if_then_else
9757        (and (match_operand 2 "const1_operand" "")
9758             (ior (match_test "TARGET_SHIFT1")
9759                  (match_test "optimize_function_for_size_p (cfun)")))
9760        (const_string "0")
9761        (const_string "*")))
9762    (set_attr "mode" "<MODE>")])
9763
9764 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9765 (define_split
9766   [(set (match_operand:SWI48 0 "register_operand" "")
9767         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9768                            (match_operand:QI 2 "register_operand" "")))
9769    (clobber (reg:CC FLAGS_REG))]
9770   "TARGET_BMI2 && reload_completed"
9771   [(set (match_dup 0)
9772         (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))]
9773   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9774
9775 (define_insn "*bmi2_<shift_insn>si3_1_zext"
9776   [(set (match_operand:DI 0 "register_operand" "=r")
9777         (zero_extend:DI
9778           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9779                           (match_operand:SI 2 "register_operand" "r"))))]
9780   "TARGET_64BIT && TARGET_BMI2"
9781   "<shift>x\t{%2, %1, %k0|%k0, %1, %2}"
9782   [(set_attr "type" "ishiftx")
9783    (set_attr "mode" "SI")])
9784
9785 (define_insn "*<shift_insn>si3_1_zext"
9786   [(set (match_operand:DI 0 "register_operand" "=r,r")
9787         (zero_extend:DI
9788           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
9789                           (match_operand:QI 2 "nonmemory_operand" "cI,r"))))
9790    (clobber (reg:CC FLAGS_REG))]
9791   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9792 {
9793   switch (get_attr_type (insn))
9794     {
9795     case TYPE_ISHIFTX:
9796       return "#";
9797
9798     default:
9799       if (operands[2] == const1_rtx
9800           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9801         return "<shift>{l}\t%k0";
9802       else
9803         return "<shift>{l}\t{%2, %k0|%k0, %2}";
9804     }
9805 }
9806   [(set_attr "isa" "*,bmi2")
9807    (set_attr "type" "ishift,ishiftx")
9808    (set (attr "length_immediate")
9809      (if_then_else
9810        (and (match_operand 2 "const1_operand" "")
9811             (ior (match_test "TARGET_SHIFT1")
9812                  (match_test "optimize_function_for_size_p (cfun)")))
9813        (const_string "0")
9814        (const_string "*")))
9815    (set_attr "mode" "SI")])
9816
9817 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9818 (define_split
9819   [(set (match_operand:DI 0 "register_operand" "")
9820         (zero_extend:DI
9821           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
9822                           (match_operand:QI 2 "register_operand" ""))))
9823    (clobber (reg:CC FLAGS_REG))]
9824   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9825   [(set (match_dup 0)
9826         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9827   "operands[2] = gen_lowpart (SImode, operands[2]);")
9828
9829 (define_insn "*<shift_insn><mode>3_1"
9830   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
9831         (any_shiftrt:SWI12
9832           (match_operand:SWI12 1 "nonimmediate_operand" "0")
9833           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
9834    (clobber (reg:CC FLAGS_REG))]
9835   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9836 {
9837   if (operands[2] == const1_rtx
9838       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9839     return "<shift>{<imodesuffix>}\t%0";
9840   else
9841     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9842 }
9843   [(set_attr "type" "ishift")
9844    (set (attr "length_immediate")
9845      (if_then_else
9846        (and (match_operand 2 "const1_operand" "")
9847             (ior (match_test "TARGET_SHIFT1")
9848                  (match_test "optimize_function_for_size_p (cfun)")))
9849        (const_string "0")
9850        (const_string "*")))
9851    (set_attr "mode" "<MODE>")])
9852
9853 (define_insn "*<shift_insn>qi3_1_slp"
9854   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9855         (any_shiftrt:QI (match_dup 0)
9856                         (match_operand:QI 1 "nonmemory_operand" "cI")))
9857    (clobber (reg:CC FLAGS_REG))]
9858   "(optimize_function_for_size_p (cfun)
9859     || !TARGET_PARTIAL_REG_STALL
9860     || (operands[1] == const1_rtx
9861         && TARGET_SHIFT1))"
9862 {
9863   if (operands[1] == const1_rtx
9864       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9865     return "<shift>{b}\t%0";
9866   else
9867     return "<shift>{b}\t{%1, %0|%0, %1}";
9868 }
9869   [(set_attr "type" "ishift1")
9870    (set (attr "length_immediate")
9871      (if_then_else
9872        (and (match_operand 1 "const1_operand" "")
9873             (ior (match_test "TARGET_SHIFT1")
9874                  (match_test "optimize_function_for_size_p (cfun)")))
9875        (const_string "0")
9876        (const_string "*")))
9877    (set_attr "mode" "QI")])
9878
9879 ;; This pattern can't accept a variable shift count, since shifts by
9880 ;; zero don't affect the flags.  We assume that shifts by constant
9881 ;; zero are optimized away.
9882 (define_insn "*<shift_insn><mode>3_cmp"
9883   [(set (reg FLAGS_REG)
9884         (compare
9885           (any_shiftrt:SWI
9886             (match_operand:SWI 1 "nonimmediate_operand" "0")
9887             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9888           (const_int 0)))
9889    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9890         (any_shiftrt:SWI (match_dup 1) (match_dup 2)))]
9891   "(optimize_function_for_size_p (cfun)
9892     || !TARGET_PARTIAL_FLAG_REG_STALL
9893     || (operands[2] == const1_rtx
9894         && TARGET_SHIFT1))
9895    && ix86_match_ccmode (insn, CCGOCmode)
9896    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9897 {
9898   if (operands[2] == const1_rtx
9899       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9900     return "<shift>{<imodesuffix>}\t%0";
9901   else
9902     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9903 }
9904   [(set_attr "type" "ishift")
9905    (set (attr "length_immediate")
9906      (if_then_else
9907        (and (match_operand 2 "const1_operand" "")
9908             (ior (match_test "TARGET_SHIFT1")
9909                  (match_test "optimize_function_for_size_p (cfun)")))
9910        (const_string "0")
9911        (const_string "*")))
9912    (set_attr "mode" "<MODE>")])
9913
9914 (define_insn "*<shift_insn>si3_cmp_zext"
9915   [(set (reg FLAGS_REG)
9916         (compare
9917           (any_shiftrt:SI (match_operand:SI 1 "register_operand" "0")
9918                           (match_operand:QI 2 "const_1_to_31_operand" "I"))
9919           (const_int 0)))
9920    (set (match_operand:DI 0 "register_operand" "=r")
9921         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9922   "TARGET_64BIT
9923    && (optimize_function_for_size_p (cfun)
9924        || !TARGET_PARTIAL_FLAG_REG_STALL
9925        || (operands[2] == const1_rtx
9926            && TARGET_SHIFT1))
9927    && ix86_match_ccmode (insn, CCGOCmode)
9928    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9929 {
9930   if (operands[2] == const1_rtx
9931       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9932     return "<shift>{l}\t%k0";
9933   else
9934     return "<shift>{l}\t{%2, %k0|%k0, %2}";
9935 }
9936   [(set_attr "type" "ishift")
9937    (set (attr "length_immediate")
9938      (if_then_else
9939        (and (match_operand 2 "const1_operand" "")
9940             (ior (match_test "TARGET_SHIFT1")
9941                  (match_test "optimize_function_for_size_p (cfun)")))
9942        (const_string "0")
9943        (const_string "*")))
9944    (set_attr "mode" "SI")])
9945
9946 (define_insn "*<shift_insn><mode>3_cconly"
9947   [(set (reg FLAGS_REG)
9948         (compare
9949           (any_shiftrt:SWI
9950             (match_operand:SWI 1 "register_operand" "0")
9951             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9952           (const_int 0)))
9953    (clobber (match_scratch:SWI 0 "=<r>"))]
9954   "(optimize_function_for_size_p (cfun)
9955     || !TARGET_PARTIAL_FLAG_REG_STALL
9956     || (operands[2] == const1_rtx
9957         && TARGET_SHIFT1))
9958    && ix86_match_ccmode (insn, CCGOCmode)"
9959 {
9960   if (operands[2] == const1_rtx
9961       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9962     return "<shift>{<imodesuffix>}\t%0";
9963   else
9964     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9965 }
9966   [(set_attr "type" "ishift")
9967    (set (attr "length_immediate")
9968      (if_then_else
9969        (and (match_operand 2 "const1_operand" "")
9970             (ior (match_test "TARGET_SHIFT1")
9971                  (match_test "optimize_function_for_size_p (cfun)")))
9972        (const_string "0")
9973        (const_string "*")))
9974    (set_attr "mode" "<MODE>")])
9975 \f
9976 ;; Rotate instructions
9977
9978 (define_expand "<rotate_insn>ti3"
9979   [(set (match_operand:TI 0 "register_operand" "")
9980         (any_rotate:TI (match_operand:TI 1 "register_operand" "")
9981                        (match_operand:QI 2 "nonmemory_operand" "")))]
9982   "TARGET_64BIT"
9983 {
9984   if (const_1_to_63_operand (operands[2], VOIDmode))
9985     emit_insn (gen_ix86_<rotate_insn>ti3_doubleword
9986                 (operands[0], operands[1], operands[2]));
9987   else
9988     FAIL;
9989
9990   DONE;
9991 })
9992
9993 (define_expand "<rotate_insn>di3"
9994   [(set (match_operand:DI 0 "shiftdi_operand" "")
9995         (any_rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
9996                        (match_operand:QI 2 "nonmemory_operand" "")))]
9997  ""
9998 {
9999   if (TARGET_64BIT)
10000     ix86_expand_binary_operator (<CODE>, DImode, operands);
10001   else if (const_1_to_31_operand (operands[2], VOIDmode))
10002     emit_insn (gen_ix86_<rotate_insn>di3_doubleword
10003                 (operands[0], operands[1], operands[2]));
10004   else
10005     FAIL;
10006
10007   DONE;
10008 })
10009
10010 (define_expand "<rotate_insn><mode>3"
10011   [(set (match_operand:SWIM124 0 "nonimmediate_operand" "")
10012         (any_rotate:SWIM124 (match_operand:SWIM124 1 "nonimmediate_operand" "")
10013                             (match_operand:QI 2 "nonmemory_operand" "")))]
10014   ""
10015   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
10016
10017 ;; Avoid useless masking of count operand.
10018 (define_insn_and_split "*<rotate_insn><mode>3_mask"
10019   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
10020         (any_rotate:SWI48
10021           (match_operand:SWI48 1 "nonimmediate_operand" "0")
10022           (subreg:QI
10023             (and:SI
10024               (match_operand:SI 2 "nonimmediate_operand" "c")
10025               (match_operand:SI 3 "const_int_operand" "n")) 0)))
10026    (clobber (reg:CC FLAGS_REG))]
10027   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
10028    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10029       == GET_MODE_BITSIZE (<MODE>mode)-1"
10030   "#"
10031   "&& 1"
10032   [(parallel [(set (match_dup 0)
10033                    (any_rotate:SWI48 (match_dup 1) (match_dup 2)))
10034               (clobber (reg:CC FLAGS_REG))])]
10035 {
10036   if (can_create_pseudo_p ())
10037     operands [2] = force_reg (SImode, operands[2]);
10038
10039   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
10040 }
10041   [(set_attr "type" "rotate")
10042    (set_attr "mode" "<MODE>")])
10043
10044 ;; Implement rotation using two double-precision
10045 ;; shift instructions and a scratch register.
10046
10047 (define_insn_and_split "ix86_rotl<dwi>3_doubleword"
10048  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10049        (rotate:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10050                      (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10051   (clobber (reg:CC FLAGS_REG))
10052   (clobber (match_scratch:DWIH 3 "=&r"))]
10053  ""
10054  "#"
10055  "reload_completed"
10056  [(set (match_dup 3) (match_dup 4))
10057   (parallel
10058    [(set (match_dup 4)
10059          (ior:DWIH (ashift:DWIH (match_dup 4) (match_dup 2))
10060                    (lshiftrt:DWIH (match_dup 5)
10061                                   (minus:QI (match_dup 6) (match_dup 2)))))
10062     (clobber (reg:CC FLAGS_REG))])
10063   (parallel
10064    [(set (match_dup 5)
10065          (ior:DWIH (ashift:DWIH (match_dup 5) (match_dup 2))
10066                    (lshiftrt:DWIH (match_dup 3)
10067                                   (minus:QI (match_dup 6) (match_dup 2)))))
10068     (clobber (reg:CC FLAGS_REG))])]
10069 {
10070   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10071
10072   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10073 })
10074
10075 (define_insn_and_split "ix86_rotr<dwi>3_doubleword"
10076  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10077        (rotatert:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10078                        (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10079   (clobber (reg:CC FLAGS_REG))
10080   (clobber (match_scratch:DWIH 3 "=&r"))]
10081  ""
10082  "#"
10083  "reload_completed"
10084  [(set (match_dup 3) (match_dup 4))
10085   (parallel
10086    [(set (match_dup 4)
10087          (ior:DWIH (ashiftrt:DWIH (match_dup 4) (match_dup 2))
10088                    (ashift:DWIH (match_dup 5)
10089                                 (minus:QI (match_dup 6) (match_dup 2)))))
10090     (clobber (reg:CC FLAGS_REG))])
10091   (parallel
10092    [(set (match_dup 5)
10093          (ior:DWIH (ashiftrt:DWIH (match_dup 5) (match_dup 2))
10094                    (ashift:DWIH (match_dup 3)
10095                                 (minus:QI (match_dup 6) (match_dup 2)))))
10096     (clobber (reg:CC FLAGS_REG))])]
10097 {
10098   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10099
10100   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10101 })
10102
10103 (define_insn "*bmi2_rorx<mode>3_1"
10104   [(set (match_operand:SWI48 0 "register_operand" "=r")
10105         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
10106                         (match_operand:QI 2 "immediate_operand" "<S>")))]
10107   "TARGET_BMI2"
10108   "rorx\t{%2, %1, %0|%0, %1, %2}"
10109   [(set_attr "type" "rotatex")
10110    (set_attr "mode" "<MODE>")])
10111
10112 (define_insn "*<rotate_insn><mode>3_1"
10113   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
10114         (any_rotate:SWI48
10115           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
10116           (match_operand:QI 2 "nonmemory_operand" "c<S>,<S>")))
10117    (clobber (reg:CC FLAGS_REG))]
10118   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10119 {
10120   switch (get_attr_type (insn))
10121     {
10122     case TYPE_ROTATEX:
10123       return "#";
10124
10125     default:
10126       if (operands[2] == const1_rtx
10127           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10128         return "<rotate>{<imodesuffix>}\t%0";
10129       else
10130         return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10131     }
10132 }
10133   [(set_attr "isa" "*,bmi2")
10134    (set_attr "type" "rotate,rotatex")
10135    (set (attr "length_immediate")
10136      (if_then_else
10137        (and (eq_attr "type" "rotate")
10138             (and (match_operand 2 "const1_operand" "")
10139                  (ior (match_test "TARGET_SHIFT1")
10140                       (match_test "optimize_function_for_size_p (cfun)"))))
10141        (const_string "0")
10142        (const_string "*")))
10143    (set_attr "mode" "<MODE>")])
10144
10145 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10146 (define_split
10147   [(set (match_operand:SWI48 0 "register_operand" "")
10148         (rotate:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10149                       (match_operand:QI 2 "immediate_operand" "")))
10150    (clobber (reg:CC FLAGS_REG))]
10151   "TARGET_BMI2 && reload_completed"
10152   [(set (match_dup 0)
10153         (rotatert:SWI48 (match_dup 1) (match_dup 2)))]
10154 {
10155   operands[2]
10156     = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - INTVAL (operands[2]));
10157 })
10158
10159 (define_split
10160   [(set (match_operand:SWI48 0 "register_operand" "")
10161         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10162                         (match_operand:QI 2 "immediate_operand" "")))
10163    (clobber (reg:CC FLAGS_REG))]
10164   "TARGET_BMI2 && reload_completed"
10165   [(set (match_dup 0)
10166         (rotatert:SWI48 (match_dup 1) (match_dup 2)))])
10167
10168 (define_insn "*bmi2_rorxsi3_1_zext"
10169   [(set (match_operand:DI 0 "register_operand" "=r")
10170         (zero_extend:DI
10171           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
10172                        (match_operand:QI 2 "immediate_operand" "I"))))]
10173   "TARGET_64BIT && TARGET_BMI2"
10174   "rorx\t{%2, %1, %k0|%k0, %1, %2}"
10175   [(set_attr "type" "rotatex")
10176    (set_attr "mode" "SI")])
10177
10178 (define_insn "*<rotate_insn>si3_1_zext"
10179   [(set (match_operand:DI 0 "register_operand" "=r,r")
10180         (zero_extend:DI
10181           (any_rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
10182                          (match_operand:QI 2 "nonmemory_operand" "cI,I"))))
10183    (clobber (reg:CC FLAGS_REG))]
10184   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
10185 {
10186   switch (get_attr_type (insn))
10187     {
10188     case TYPE_ROTATEX:
10189       return "#";
10190
10191     default:
10192       if (operands[2] == const1_rtx
10193           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10194         return "<rotate>{l}\t%k0";
10195       else
10196         return "<rotate>{l}\t{%2, %k0|%k0, %2}";
10197     }
10198 }
10199   [(set_attr "isa" "*,bmi2")
10200    (set_attr "type" "rotate,rotatex")
10201    (set (attr "length_immediate")
10202      (if_then_else
10203        (and (eq_attr "type" "rotate")
10204             (and (match_operand 2 "const1_operand" "")
10205                  (ior (match_test "TARGET_SHIFT1")
10206                       (match_test "optimize_function_for_size_p (cfun)"))))
10207        (const_string "0")
10208        (const_string "*")))
10209    (set_attr "mode" "SI")])
10210
10211 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10212 (define_split
10213   [(set (match_operand:DI 0 "register_operand" "")
10214         (zero_extend:DI
10215           (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
10216                      (match_operand:QI 2 "immediate_operand" ""))))
10217    (clobber (reg:CC FLAGS_REG))]
10218   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10219   [(set (match_dup 0)
10220         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))]
10221 {
10222   operands[2]
10223     = GEN_INT (GET_MODE_BITSIZE (SImode) - INTVAL (operands[2]));
10224 })
10225
10226 (define_split
10227   [(set (match_operand:DI 0 "register_operand" "")
10228         (zero_extend:DI
10229           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
10230                        (match_operand:QI 2 "immediate_operand" ""))))
10231    (clobber (reg:CC FLAGS_REG))]
10232   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10233   [(set (match_dup 0)
10234         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))])
10235
10236 (define_insn "*<rotate_insn><mode>3_1"
10237   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
10238         (any_rotate:SWI12 (match_operand:SWI12 1 "nonimmediate_operand" "0")
10239                           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
10240    (clobber (reg:CC FLAGS_REG))]
10241   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10242 {
10243   if (operands[2] == const1_rtx
10244       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10245     return "<rotate>{<imodesuffix>}\t%0";
10246   else
10247     return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10248 }
10249   [(set_attr "type" "rotate")
10250    (set (attr "length_immediate")
10251      (if_then_else
10252        (and (match_operand 2 "const1_operand" "")
10253             (ior (match_test "TARGET_SHIFT1")
10254                  (match_test "optimize_function_for_size_p (cfun)")))
10255        (const_string "0")
10256        (const_string "*")))
10257    (set_attr "mode" "<MODE>")])
10258
10259 (define_insn "*<rotate_insn>qi3_1_slp"
10260   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10261         (any_rotate:QI (match_dup 0)
10262                        (match_operand:QI 1 "nonmemory_operand" "cI")))
10263    (clobber (reg:CC FLAGS_REG))]
10264   "(optimize_function_for_size_p (cfun)
10265     || !TARGET_PARTIAL_REG_STALL
10266     || (operands[1] == const1_rtx
10267         && TARGET_SHIFT1))"
10268 {
10269   if (operands[1] == const1_rtx
10270       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10271     return "<rotate>{b}\t%0";
10272   else
10273     return "<rotate>{b}\t{%1, %0|%0, %1}";
10274 }
10275   [(set_attr "type" "rotate1")
10276    (set (attr "length_immediate")
10277      (if_then_else
10278        (and (match_operand 1 "const1_operand" "")
10279             (ior (match_test "TARGET_SHIFT1")
10280                  (match_test "optimize_function_for_size_p (cfun)")))
10281        (const_string "0")
10282        (const_string "*")))
10283    (set_attr "mode" "QI")])
10284
10285 (define_split
10286  [(set (match_operand:HI 0 "register_operand" "")
10287        (any_rotate:HI (match_dup 0) (const_int 8)))
10288   (clobber (reg:CC FLAGS_REG))]
10289  "reload_completed
10290   && (TARGET_USE_XCHGB || optimize_function_for_size_p (cfun))"
10291  [(parallel [(set (strict_low_part (match_dup 0))
10292                   (bswap:HI (match_dup 0)))
10293              (clobber (reg:CC FLAGS_REG))])])
10294 \f
10295 ;; Bit set / bit test instructions
10296
10297 (define_expand "extv"
10298   [(set (match_operand:SI 0 "register_operand" "")
10299         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
10300                          (match_operand:SI 2 "const8_operand" "")
10301                          (match_operand:SI 3 "const8_operand" "")))]
10302   ""
10303 {
10304   /* Handle extractions from %ah et al.  */
10305   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10306     FAIL;
10307
10308   /* From mips.md: extract_bit_field doesn't verify that our source
10309      matches the predicate, so check it again here.  */
10310   if (! ext_register_operand (operands[1], VOIDmode))
10311     FAIL;
10312 })
10313
10314 (define_expand "extzv"
10315   [(set (match_operand:SI 0 "register_operand" "")
10316         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
10317                          (match_operand:SI 2 "const8_operand" "")
10318                          (match_operand:SI 3 "const8_operand" "")))]
10319   ""
10320 {
10321   /* Handle extractions from %ah et al.  */
10322   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10323     FAIL;
10324
10325   /* From mips.md: extract_bit_field doesn't verify that our source
10326      matches the predicate, so check it again here.  */
10327   if (! ext_register_operand (operands[1], VOIDmode))
10328     FAIL;
10329 })
10330
10331 (define_expand "insv"
10332   [(set (zero_extract (match_operand 0 "register_operand" "")
10333                       (match_operand 1 "const_int_operand" "")
10334                       (match_operand 2 "const_int_operand" ""))
10335         (match_operand 3 "register_operand" ""))]
10336   ""
10337 {
10338   rtx (*gen_mov_insv_1) (rtx, rtx);
10339
10340   if (ix86_expand_pinsr (operands))
10341     DONE;
10342
10343   /* Handle insertions to %ah et al.  */
10344   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
10345     FAIL;
10346
10347   /* From mips.md: insert_bit_field doesn't verify that our source
10348      matches the predicate, so check it again here.  */
10349   if (! ext_register_operand (operands[0], VOIDmode))
10350     FAIL;
10351
10352   gen_mov_insv_1 = (TARGET_64BIT
10353                     ? gen_movdi_insv_1 : gen_movsi_insv_1);
10354
10355   emit_insn (gen_mov_insv_1 (operands[0], operands[3]));
10356   DONE;
10357 })
10358
10359 ;; %%% bts, btr, btc, bt.
10360 ;; In general these instructions are *slow* when applied to memory,
10361 ;; since they enforce atomic operation.  When applied to registers,
10362 ;; it depends on the cpu implementation.  They're never faster than
10363 ;; the corresponding and/ior/xor operations, so with 32-bit there's
10364 ;; no point.  But in 64-bit, we can't hold the relevant immediates
10365 ;; within the instruction itself, so operating on bits in the high
10366 ;; 32-bits of a register becomes easier.
10367 ;;
10368 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
10369 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
10370 ;; negdf respectively, so they can never be disabled entirely.
10371
10372 (define_insn "*btsq"
10373   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10374                          (const_int 1)
10375                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10376         (const_int 1))
10377    (clobber (reg:CC FLAGS_REG))]
10378   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10379   "bts{q}\t{%1, %0|%0, %1}"
10380   [(set_attr "type" "alu1")
10381    (set_attr "prefix_0f" "1")
10382    (set_attr "mode" "DI")])
10383
10384 (define_insn "*btrq"
10385   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10386                          (const_int 1)
10387                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10388         (const_int 0))
10389    (clobber (reg:CC FLAGS_REG))]
10390   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10391   "btr{q}\t{%1, %0|%0, %1}"
10392   [(set_attr "type" "alu1")
10393    (set_attr "prefix_0f" "1")
10394    (set_attr "mode" "DI")])
10395
10396 (define_insn "*btcq"
10397   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10398                          (const_int 1)
10399                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10400         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
10401    (clobber (reg:CC FLAGS_REG))]
10402   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10403   "btc{q}\t{%1, %0|%0, %1}"
10404   [(set_attr "type" "alu1")
10405    (set_attr "prefix_0f" "1")
10406    (set_attr "mode" "DI")])
10407
10408 ;; Allow Nocona to avoid these instructions if a register is available.
10409
10410 (define_peephole2
10411   [(match_scratch:DI 2 "r")
10412    (parallel [(set (zero_extract:DI
10413                      (match_operand:DI 0 "register_operand" "")
10414                      (const_int 1)
10415                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10416                    (const_int 1))
10417               (clobber (reg:CC FLAGS_REG))])]
10418   "TARGET_64BIT && !TARGET_USE_BT"
10419   [(const_int 0)]
10420 {
10421   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10422   rtx op1;
10423
10424   if (HOST_BITS_PER_WIDE_INT >= 64)
10425     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10426   else if (i < HOST_BITS_PER_WIDE_INT)
10427     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10428   else
10429     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10430
10431   op1 = immed_double_const (lo, hi, DImode);
10432   if (i >= 31)
10433     {
10434       emit_move_insn (operands[2], op1);
10435       op1 = operands[2];
10436     }
10437
10438   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
10439   DONE;
10440 })
10441
10442 (define_peephole2
10443   [(match_scratch:DI 2 "r")
10444    (parallel [(set (zero_extract:DI
10445                      (match_operand:DI 0 "register_operand" "")
10446                      (const_int 1)
10447                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10448                    (const_int 0))
10449               (clobber (reg:CC FLAGS_REG))])]
10450   "TARGET_64BIT && !TARGET_USE_BT"
10451   [(const_int 0)]
10452 {
10453   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10454   rtx op1;
10455
10456   if (HOST_BITS_PER_WIDE_INT >= 64)
10457     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10458   else if (i < HOST_BITS_PER_WIDE_INT)
10459     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10460   else
10461     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10462
10463   op1 = immed_double_const (~lo, ~hi, DImode);
10464   if (i >= 32)
10465     {
10466       emit_move_insn (operands[2], op1);
10467       op1 = operands[2];
10468     }
10469
10470   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
10471   DONE;
10472 })
10473
10474 (define_peephole2
10475   [(match_scratch:DI 2 "r")
10476    (parallel [(set (zero_extract:DI
10477                      (match_operand:DI 0 "register_operand" "")
10478                      (const_int 1)
10479                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10480               (not:DI (zero_extract:DI
10481                         (match_dup 0) (const_int 1) (match_dup 1))))
10482               (clobber (reg:CC FLAGS_REG))])]
10483   "TARGET_64BIT && !TARGET_USE_BT"
10484   [(const_int 0)]
10485 {
10486   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10487   rtx op1;
10488
10489   if (HOST_BITS_PER_WIDE_INT >= 64)
10490     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10491   else if (i < HOST_BITS_PER_WIDE_INT)
10492     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10493   else
10494     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10495
10496   op1 = immed_double_const (lo, hi, DImode);
10497   if (i >= 31)
10498     {
10499       emit_move_insn (operands[2], op1);
10500       op1 = operands[2];
10501     }
10502
10503   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
10504   DONE;
10505 })
10506
10507 (define_insn "*bt<mode>"
10508   [(set (reg:CCC FLAGS_REG)
10509         (compare:CCC
10510           (zero_extract:SWI48
10511             (match_operand:SWI48 0 "register_operand" "r")
10512             (const_int 1)
10513             (match_operand:SWI48 1 "x86_64_nonmemory_operand" "rN"))
10514           (const_int 0)))]
10515   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10516   "bt{<imodesuffix>}\t{%1, %0|%0, %1}"
10517   [(set_attr "type" "alu1")
10518    (set_attr "prefix_0f" "1")
10519    (set_attr "mode" "<MODE>")])
10520 \f
10521 ;; Store-flag instructions.
10522
10523 ;; For all sCOND expanders, also expand the compare or test insn that
10524 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
10525
10526 (define_insn_and_split "*setcc_di_1"
10527   [(set (match_operand:DI 0 "register_operand" "=q")
10528         (match_operator:DI 1 "ix86_comparison_operator"
10529           [(reg FLAGS_REG) (const_int 0)]))]
10530   "TARGET_64BIT && !TARGET_PARTIAL_REG_STALL"
10531   "#"
10532   "&& reload_completed"
10533   [(set (match_dup 2) (match_dup 1))
10534    (set (match_dup 0) (zero_extend:DI (match_dup 2)))]
10535 {
10536   PUT_MODE (operands[1], QImode);
10537   operands[2] = gen_lowpart (QImode, operands[0]);
10538 })
10539
10540 (define_insn_and_split "*setcc_si_1_and"
10541   [(set (match_operand:SI 0 "register_operand" "=q")
10542         (match_operator:SI 1 "ix86_comparison_operator"
10543           [(reg FLAGS_REG) (const_int 0)]))
10544    (clobber (reg:CC FLAGS_REG))]
10545   "!TARGET_PARTIAL_REG_STALL
10546    && TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
10547   "#"
10548   "&& reload_completed"
10549   [(set (match_dup 2) (match_dup 1))
10550    (parallel [(set (match_dup 0) (zero_extend:SI (match_dup 2)))
10551               (clobber (reg:CC FLAGS_REG))])]
10552 {
10553   PUT_MODE (operands[1], QImode);
10554   operands[2] = gen_lowpart (QImode, operands[0]);
10555 })
10556
10557 (define_insn_and_split "*setcc_si_1_movzbl"
10558   [(set (match_operand:SI 0 "register_operand" "=q")
10559         (match_operator:SI 1 "ix86_comparison_operator"
10560           [(reg FLAGS_REG) (const_int 0)]))]
10561   "!TARGET_PARTIAL_REG_STALL
10562    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
10563   "#"
10564   "&& reload_completed"
10565   [(set (match_dup 2) (match_dup 1))
10566    (set (match_dup 0) (zero_extend:SI (match_dup 2)))]
10567 {
10568   PUT_MODE (operands[1], QImode);
10569   operands[2] = gen_lowpart (QImode, operands[0]);
10570 })
10571
10572 (define_insn "*setcc_qi"
10573   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10574         (match_operator:QI 1 "ix86_comparison_operator"
10575           [(reg FLAGS_REG) (const_int 0)]))]
10576   ""
10577   "set%C1\t%0"
10578   [(set_attr "type" "setcc")
10579    (set_attr "mode" "QI")])
10580
10581 (define_insn "*setcc_qi_slp"
10582   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10583         (match_operator:QI 1 "ix86_comparison_operator"
10584           [(reg FLAGS_REG) (const_int 0)]))]
10585   ""
10586   "set%C1\t%0"
10587   [(set_attr "type" "setcc")
10588    (set_attr "mode" "QI")])
10589
10590 ;; In general it is not safe to assume too much about CCmode registers,
10591 ;; so simplify-rtx stops when it sees a second one.  Under certain
10592 ;; conditions this is safe on x86, so help combine not create
10593 ;;
10594 ;;      seta    %al
10595 ;;      testb   %al, %al
10596 ;;      sete    %al
10597
10598 (define_split
10599   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10600         (ne:QI (match_operator 1 "ix86_comparison_operator"
10601                  [(reg FLAGS_REG) (const_int 0)])
10602             (const_int 0)))]
10603   ""
10604   [(set (match_dup 0) (match_dup 1))]
10605   "PUT_MODE (operands[1], QImode);")
10606
10607 (define_split
10608   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10609         (ne:QI (match_operator 1 "ix86_comparison_operator"
10610                  [(reg FLAGS_REG) (const_int 0)])
10611             (const_int 0)))]
10612   ""
10613   [(set (match_dup 0) (match_dup 1))]
10614   "PUT_MODE (operands[1], QImode);")
10615
10616 (define_split
10617   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10618         (eq:QI (match_operator 1 "ix86_comparison_operator"
10619                  [(reg FLAGS_REG) (const_int 0)])
10620             (const_int 0)))]
10621   ""
10622   [(set (match_dup 0) (match_dup 1))]
10623 {
10624   rtx new_op1 = copy_rtx (operands[1]);
10625   operands[1] = new_op1;
10626   PUT_MODE (new_op1, QImode);
10627   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10628                                              GET_MODE (XEXP (new_op1, 0))));
10629
10630   /* Make sure that (a) the CCmode we have for the flags is strong
10631      enough for the reversed compare or (b) we have a valid FP compare.  */
10632   if (! ix86_comparison_operator (new_op1, VOIDmode))
10633     FAIL;
10634 })
10635
10636 (define_split
10637   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10638         (eq:QI (match_operator 1 "ix86_comparison_operator"
10639                  [(reg FLAGS_REG) (const_int 0)])
10640             (const_int 0)))]
10641   ""
10642   [(set (match_dup 0) (match_dup 1))]
10643 {
10644   rtx new_op1 = copy_rtx (operands[1]);
10645   operands[1] = new_op1;
10646   PUT_MODE (new_op1, QImode);
10647   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10648                                              GET_MODE (XEXP (new_op1, 0))));
10649
10650   /* Make sure that (a) the CCmode we have for the flags is strong
10651      enough for the reversed compare or (b) we have a valid FP compare.  */
10652   if (! ix86_comparison_operator (new_op1, VOIDmode))
10653     FAIL;
10654 })
10655
10656 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
10657 ;; subsequent logical operations are used to imitate conditional moves.
10658 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
10659 ;; it directly.
10660
10661 (define_insn "setcc_<mode>_sse"
10662   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
10663         (match_operator:MODEF 3 "sse_comparison_operator"
10664           [(match_operand:MODEF 1 "register_operand" "0,x")
10665            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
10666   "SSE_FLOAT_MODE_P (<MODE>mode)"
10667   "@
10668    cmp%D3<ssemodesuffix>\t{%2, %0|%0, %2}
10669    vcmp%D3<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
10670   [(set_attr "isa" "noavx,avx")
10671    (set_attr "type" "ssecmp")
10672    (set_attr "length_immediate" "1")
10673    (set_attr "prefix" "orig,vex")
10674    (set_attr "mode" "<MODE>")])
10675 \f
10676 ;; Basic conditional jump instructions.
10677 ;; We ignore the overflow flag for signed branch instructions.
10678
10679 (define_insn "*jcc_1"
10680   [(set (pc)
10681         (if_then_else (match_operator 1 "ix86_comparison_operator"
10682                                       [(reg FLAGS_REG) (const_int 0)])
10683                       (label_ref (match_operand 0 "" ""))
10684                       (pc)))]
10685   ""
10686   "%+j%C1\t%l0"
10687   [(set_attr "type" "ibr")
10688    (set_attr "modrm" "0")
10689    (set (attr "length")
10690            (if_then_else (and (ge (minus (match_dup 0) (pc))
10691                                   (const_int -126))
10692                               (lt (minus (match_dup 0) (pc))
10693                                   (const_int 128)))
10694              (const_int 2)
10695              (const_int 6)))])
10696
10697 (define_insn "*jcc_2"
10698   [(set (pc)
10699         (if_then_else (match_operator 1 "ix86_comparison_operator"
10700                                       [(reg FLAGS_REG) (const_int 0)])
10701                       (pc)
10702                       (label_ref (match_operand 0 "" ""))))]
10703   ""
10704   "%+j%c1\t%l0"
10705   [(set_attr "type" "ibr")
10706    (set_attr "modrm" "0")
10707    (set (attr "length")
10708            (if_then_else (and (ge (minus (match_dup 0) (pc))
10709                                   (const_int -126))
10710                               (lt (minus (match_dup 0) (pc))
10711                                   (const_int 128)))
10712              (const_int 2)
10713              (const_int 6)))])
10714
10715 ;; In general it is not safe to assume too much about CCmode registers,
10716 ;; so simplify-rtx stops when it sees a second one.  Under certain
10717 ;; conditions this is safe on x86, so help combine not create
10718 ;;
10719 ;;      seta    %al
10720 ;;      testb   %al, %al
10721 ;;      je      Lfoo
10722
10723 (define_split
10724   [(set (pc)
10725         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
10726                                       [(reg FLAGS_REG) (const_int 0)])
10727                           (const_int 0))
10728                       (label_ref (match_operand 1 "" ""))
10729                       (pc)))]
10730   ""
10731   [(set (pc)
10732         (if_then_else (match_dup 0)
10733                       (label_ref (match_dup 1))
10734                       (pc)))]
10735   "PUT_MODE (operands[0], VOIDmode);")
10736
10737 (define_split
10738   [(set (pc)
10739         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
10740                                       [(reg FLAGS_REG) (const_int 0)])
10741                           (const_int 0))
10742                       (label_ref (match_operand 1 "" ""))
10743                       (pc)))]
10744   ""
10745   [(set (pc)
10746         (if_then_else (match_dup 0)
10747                       (label_ref (match_dup 1))
10748                       (pc)))]
10749 {
10750   rtx new_op0 = copy_rtx (operands[0]);
10751   operands[0] = new_op0;
10752   PUT_MODE (new_op0, VOIDmode);
10753   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
10754                                              GET_MODE (XEXP (new_op0, 0))));
10755
10756   /* Make sure that (a) the CCmode we have for the flags is strong
10757      enough for the reversed compare or (b) we have a valid FP compare.  */
10758   if (! ix86_comparison_operator (new_op0, VOIDmode))
10759     FAIL;
10760 })
10761
10762 ;; zero_extend in SImode is correct also for DImode, since this is what combine
10763 ;; pass generates from shift insn with QImode operand.  Actually, the mode
10764 ;; of operand 2 (bit offset operand) doesn't matter since bt insn takes
10765 ;; appropriate modulo of the bit offset value.
10766
10767 (define_insn_and_split "*jcc_bt<mode>"
10768   [(set (pc)
10769         (if_then_else (match_operator 0 "bt_comparison_operator"
10770                         [(zero_extract:SWI48
10771                            (match_operand:SWI48 1 "register_operand" "r")
10772                            (const_int 1)
10773                            (zero_extend:SI
10774                              (match_operand:QI 2 "register_operand" "r")))
10775                          (const_int 0)])
10776                       (label_ref (match_operand 3 "" ""))
10777                       (pc)))
10778    (clobber (reg:CC FLAGS_REG))]
10779   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10780   "#"
10781   "&& 1"
10782   [(set (reg:CCC FLAGS_REG)
10783         (compare:CCC
10784           (zero_extract:SWI48
10785             (match_dup 1)
10786             (const_int 1)
10787             (match_dup 2))
10788           (const_int 0)))
10789    (set (pc)
10790         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10791                       (label_ref (match_dup 3))
10792                       (pc)))]
10793 {
10794   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], QImode, 0);
10795
10796   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10797 })
10798
10799 ;; Avoid useless masking of bit offset operand.  "and" in SImode is correct
10800 ;; also for DImode, this is what combine produces.
10801 (define_insn_and_split "*jcc_bt<mode>_mask"
10802   [(set (pc)
10803         (if_then_else (match_operator 0 "bt_comparison_operator"
10804                         [(zero_extract:SWI48
10805                            (match_operand:SWI48 1 "register_operand" "r")
10806                            (const_int 1)
10807                            (and:SI
10808                              (match_operand:SI 2 "register_operand" "r")
10809                              (match_operand:SI 3 "const_int_operand" "n")))])
10810                       (label_ref (match_operand 4 "" ""))
10811                       (pc)))
10812    (clobber (reg:CC FLAGS_REG))]
10813   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10814    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10815       == GET_MODE_BITSIZE (<MODE>mode)-1"
10816   "#"
10817   "&& 1"
10818   [(set (reg:CCC FLAGS_REG)
10819         (compare:CCC
10820           (zero_extract:SWI48
10821             (match_dup 1)
10822             (const_int 1)
10823             (match_dup 2))
10824           (const_int 0)))
10825    (set (pc)
10826         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10827                       (label_ref (match_dup 4))
10828                       (pc)))]
10829 {
10830   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], SImode, 0);
10831
10832   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10833 })
10834
10835 (define_insn_and_split "*jcc_btsi_1"
10836   [(set (pc)
10837         (if_then_else (match_operator 0 "bt_comparison_operator"
10838                         [(and:SI
10839                            (lshiftrt:SI
10840                              (match_operand:SI 1 "register_operand" "r")
10841                              (match_operand:QI 2 "register_operand" "r"))
10842                            (const_int 1))
10843                          (const_int 0)])
10844                       (label_ref (match_operand 3 "" ""))
10845                       (pc)))
10846    (clobber (reg:CC FLAGS_REG))]
10847   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10848   "#"
10849   "&& 1"
10850   [(set (reg:CCC FLAGS_REG)
10851         (compare:CCC
10852           (zero_extract:SI
10853             (match_dup 1)
10854             (const_int 1)
10855             (match_dup 2))
10856           (const_int 0)))
10857    (set (pc)
10858         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10859                       (label_ref (match_dup 3))
10860                       (pc)))]
10861 {
10862   operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
10863
10864   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10865 })
10866
10867 ;; avoid useless masking of bit offset operand
10868 (define_insn_and_split "*jcc_btsi_mask_1"
10869   [(set (pc)
10870         (if_then_else
10871           (match_operator 0 "bt_comparison_operator"
10872             [(and:SI
10873                (lshiftrt:SI
10874                  (match_operand:SI 1 "register_operand" "r")
10875                  (subreg:QI
10876                    (and:SI
10877                      (match_operand:SI 2 "register_operand" "r")
10878                      (match_operand:SI 3 "const_int_operand" "n")) 0))
10879                (const_int 1))
10880              (const_int 0)])
10881           (label_ref (match_operand 4 "" ""))
10882           (pc)))
10883    (clobber (reg:CC FLAGS_REG))]
10884   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10885    && (INTVAL (operands[3]) & 0x1f) == 0x1f"
10886   "#"
10887   "&& 1"
10888   [(set (reg:CCC FLAGS_REG)
10889         (compare:CCC
10890           (zero_extract:SI
10891             (match_dup 1)
10892             (const_int 1)
10893             (match_dup 2))
10894           (const_int 0)))
10895    (set (pc)
10896         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10897                       (label_ref (match_dup 4))
10898                       (pc)))]
10899   "PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));")
10900
10901 ;; Define combination compare-and-branch fp compare instructions to help
10902 ;; combine.
10903
10904 (define_insn "*fp_jcc_1_387"
10905   [(set (pc)
10906         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10907                         [(match_operand 1 "register_operand" "f")
10908                          (match_operand 2 "nonimmediate_operand" "fm")])
10909           (label_ref (match_operand 3 "" ""))
10910           (pc)))
10911    (clobber (reg:CCFP FPSR_REG))
10912    (clobber (reg:CCFP FLAGS_REG))
10913    (clobber (match_scratch:HI 4 "=a"))]
10914   "TARGET_80387
10915    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10916    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10917    && SELECT_CC_MODE (GET_CODE (operands[0]),
10918                       operands[1], operands[2]) == CCFPmode
10919    && !TARGET_CMOVE"
10920   "#")
10921
10922 (define_insn "*fp_jcc_1r_387"
10923   [(set (pc)
10924         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10925                         [(match_operand 1 "register_operand" "f")
10926                          (match_operand 2 "nonimmediate_operand" "fm")])
10927           (pc)
10928           (label_ref (match_operand 3 "" ""))))
10929    (clobber (reg:CCFP FPSR_REG))
10930    (clobber (reg:CCFP FLAGS_REG))
10931    (clobber (match_scratch:HI 4 "=a"))]
10932   "TARGET_80387
10933    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10934    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10935    && SELECT_CC_MODE (GET_CODE (operands[0]),
10936                       operands[1], operands[2]) == CCFPmode
10937    && !TARGET_CMOVE"
10938   "#")
10939
10940 (define_insn "*fp_jcc_2_387"
10941   [(set (pc)
10942         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10943                         [(match_operand 1 "register_operand" "f")
10944                          (match_operand 2 "register_operand" "f")])
10945           (label_ref (match_operand 3 "" ""))
10946           (pc)))
10947    (clobber (reg:CCFP FPSR_REG))
10948    (clobber (reg:CCFP FLAGS_REG))
10949    (clobber (match_scratch:HI 4 "=a"))]
10950   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10951    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10952    && !TARGET_CMOVE"
10953   "#")
10954
10955 (define_insn "*fp_jcc_2r_387"
10956   [(set (pc)
10957         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10958                         [(match_operand 1 "register_operand" "f")
10959                          (match_operand 2 "register_operand" "f")])
10960           (pc)
10961           (label_ref (match_operand 3 "" ""))))
10962    (clobber (reg:CCFP FPSR_REG))
10963    (clobber (reg:CCFP FLAGS_REG))
10964    (clobber (match_scratch:HI 4 "=a"))]
10965   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10966    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10967    && !TARGET_CMOVE"
10968   "#")
10969
10970 (define_insn "*fp_jcc_3_387"
10971   [(set (pc)
10972         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10973                         [(match_operand 1 "register_operand" "f")
10974                          (match_operand 2 "const0_operand" "")])
10975           (label_ref (match_operand 3 "" ""))
10976           (pc)))
10977    (clobber (reg:CCFP FPSR_REG))
10978    (clobber (reg:CCFP FLAGS_REG))
10979    (clobber (match_scratch:HI 4 "=a"))]
10980   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10981    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10982    && SELECT_CC_MODE (GET_CODE (operands[0]),
10983                       operands[1], operands[2]) == CCFPmode
10984    && !TARGET_CMOVE"
10985   "#")
10986
10987 (define_split
10988   [(set (pc)
10989         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10990                         [(match_operand 1 "register_operand" "")
10991                          (match_operand 2 "nonimmediate_operand" "")])
10992           (match_operand 3 "" "")
10993           (match_operand 4 "" "")))
10994    (clobber (reg:CCFP FPSR_REG))
10995    (clobber (reg:CCFP FLAGS_REG))]
10996   "reload_completed"
10997   [(const_int 0)]
10998 {
10999   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
11000                         operands[3], operands[4], NULL_RTX, NULL_RTX);
11001   DONE;
11002 })
11003
11004 (define_split
11005   [(set (pc)
11006         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
11007                         [(match_operand 1 "register_operand" "")
11008                          (match_operand 2 "general_operand" "")])
11009           (match_operand 3 "" "")
11010           (match_operand 4 "" "")))
11011    (clobber (reg:CCFP FPSR_REG))
11012    (clobber (reg:CCFP FLAGS_REG))
11013    (clobber (match_scratch:HI 5 "=a"))]
11014   "reload_completed"
11015   [(const_int 0)]
11016 {
11017   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
11018                         operands[3], operands[4], operands[5], NULL_RTX);
11019   DONE;
11020 })
11021
11022 ;; The order of operands in *fp_jcc_4_387 is forced by combine in
11023 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
11024 ;; with a precedence over other operators and is always put in the first
11025 ;; place. Swap condition and operands to match ficom instruction.
11026
11027 (define_insn "*fp_jcc_4_<mode>_387"
11028   [(set (pc)
11029         (if_then_else
11030           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11031             [(match_operator 1 "float_operator"
11032               [(match_operand:SWI24 2 "nonimmediate_operand" "m,?r")])
11033              (match_operand 3 "register_operand" "f,f")])
11034           (label_ref (match_operand 4 "" ""))
11035           (pc)))
11036    (clobber (reg:CCFP FPSR_REG))
11037    (clobber (reg:CCFP FLAGS_REG))
11038    (clobber (match_scratch:HI 5 "=a,a"))]
11039   "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
11040    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
11041    && GET_MODE (operands[1]) == GET_MODE (operands[3])
11042    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
11043    && !TARGET_CMOVE"
11044   "#")
11045
11046 (define_split
11047   [(set (pc)
11048         (if_then_else
11049           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11050             [(match_operator 1 "float_operator"
11051               [(match_operand:SWI24 2 "memory_operand" "")])
11052              (match_operand 3 "register_operand" "")])
11053           (match_operand 4 "" "")
11054           (match_operand 5 "" "")))
11055    (clobber (reg:CCFP FPSR_REG))
11056    (clobber (reg:CCFP FLAGS_REG))
11057    (clobber (match_scratch:HI 6 "=a"))]
11058   "reload_completed"
11059   [(const_int 0)]
11060 {
11061   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
11062
11063   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11064                         operands[3], operands[7],
11065                         operands[4], operands[5], operands[6], NULL_RTX);
11066   DONE;
11067 })
11068
11069 ;; %%% Kill this when reload knows how to do it.
11070 (define_split
11071   [(set (pc)
11072         (if_then_else
11073           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11074             [(match_operator 1 "float_operator"
11075               [(match_operand:SWI24 2 "register_operand" "")])
11076              (match_operand 3 "register_operand" "")])
11077           (match_operand 4 "" "")
11078           (match_operand 5 "" "")))
11079    (clobber (reg:CCFP FPSR_REG))
11080    (clobber (reg:CCFP FLAGS_REG))
11081    (clobber (match_scratch:HI 6 "=a"))]
11082   "reload_completed"
11083   [(const_int 0)]
11084 {
11085   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
11086   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
11087
11088   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11089                         operands[3], operands[7],
11090                         operands[4], operands[5], operands[6], operands[2]);
11091   DONE;
11092 })
11093 \f
11094 ;; Unconditional and other jump instructions
11095
11096 (define_insn "jump"
11097   [(set (pc)
11098         (label_ref (match_operand 0 "" "")))]
11099   ""
11100   "jmp\t%l0"
11101   [(set_attr "type" "ibr")
11102    (set (attr "length")
11103            (if_then_else (and (ge (minus (match_dup 0) (pc))
11104                                   (const_int -126))
11105                               (lt (minus (match_dup 0) (pc))
11106                                   (const_int 128)))
11107              (const_int 2)
11108              (const_int 5)))
11109    (set_attr "modrm" "0")])
11110
11111 (define_expand "indirect_jump"
11112   [(set (pc) (match_operand 0 "indirect_branch_operand" ""))])
11113
11114 (define_insn "*indirect_jump"
11115   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))]
11116   ""
11117   "jmp\t%A0"
11118   [(set_attr "type" "ibr")
11119    (set_attr "length_immediate" "0")])
11120
11121 (define_expand "tablejump"
11122   [(parallel [(set (pc) (match_operand 0 "indirect_branch_operand" ""))
11123               (use (label_ref (match_operand 1 "" "")))])]
11124   ""
11125 {
11126   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
11127      relative.  Convert the relative address to an absolute address.  */
11128   if (flag_pic)
11129     {
11130       rtx op0, op1;
11131       enum rtx_code code;
11132
11133       /* We can't use @GOTOFF for text labels on VxWorks;
11134          see gotoff_operand.  */
11135       if (TARGET_64BIT || TARGET_VXWORKS_RTP)
11136         {
11137           code = PLUS;
11138           op0 = operands[0];
11139           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
11140         }
11141       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
11142         {
11143           code = PLUS;
11144           op0 = operands[0];
11145           op1 = pic_offset_table_rtx;
11146         }
11147       else
11148         {
11149           code = MINUS;
11150           op0 = pic_offset_table_rtx;
11151           op1 = operands[0];
11152         }
11153
11154       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
11155                                          OPTAB_DIRECT);
11156     }
11157   else if (TARGET_X32)
11158     operands[0] = convert_memory_address (Pmode, operands[0]);
11159 })
11160
11161 (define_insn "*tablejump_1"
11162   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))
11163    (use (label_ref (match_operand 1 "" "")))]
11164   ""
11165   "jmp\t%A0"
11166   [(set_attr "type" "ibr")
11167    (set_attr "length_immediate" "0")])
11168 \f
11169 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
11170
11171 (define_peephole2
11172   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11173    (set (match_operand:QI 1 "register_operand" "")
11174         (match_operator:QI 2 "ix86_comparison_operator"
11175           [(reg FLAGS_REG) (const_int 0)]))
11176    (set (match_operand 3 "q_regs_operand" "")
11177         (zero_extend (match_dup 1)))]
11178   "(peep2_reg_dead_p (3, operands[1])
11179     || operands_match_p (operands[1], operands[3]))
11180    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11181   [(set (match_dup 4) (match_dup 0))
11182    (set (strict_low_part (match_dup 5))
11183         (match_dup 2))]
11184 {
11185   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11186   operands[5] = gen_lowpart (QImode, operands[3]);
11187   ix86_expand_clear (operands[3]);
11188 })
11189
11190 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
11191
11192 (define_peephole2
11193   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11194    (set (match_operand:QI 1 "register_operand" "")
11195         (match_operator:QI 2 "ix86_comparison_operator"
11196           [(reg FLAGS_REG) (const_int 0)]))
11197    (parallel [(set (match_operand 3 "q_regs_operand" "")
11198                    (zero_extend (match_dup 1)))
11199               (clobber (reg:CC FLAGS_REG))])]
11200   "(peep2_reg_dead_p (3, operands[1])
11201     || operands_match_p (operands[1], operands[3]))
11202    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11203   [(set (match_dup 4) (match_dup 0))
11204    (set (strict_low_part (match_dup 5))
11205         (match_dup 2))]
11206 {
11207   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11208   operands[5] = gen_lowpart (QImode, operands[3]);
11209   ix86_expand_clear (operands[3]);
11210 })
11211 \f
11212 ;; Call instructions.
11213
11214 ;; The predicates normally associated with named expanders are not properly
11215 ;; checked for calls.  This is a bug in the generic code, but it isn't that
11216 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
11217
11218 ;; P6 processors will jump to the address after the decrement when %esp
11219 ;; is used as a call operand, so they will execute return address as a code.
11220 ;; See Pentium Pro errata 70, Pentium 2 errata A33 and Pentium 3 errata E17.
11221
11222 ;; Register constraint for call instruction.
11223 (define_mode_attr c [(SI "l") (DI "r")])
11224
11225 ;; Call subroutine returning no value.
11226
11227 (define_expand "call"
11228   [(call (match_operand:QI 0 "" "")
11229          (match_operand 1 "" ""))
11230    (use (match_operand 2 "" ""))]
11231   ""
11232 {
11233   ix86_expand_call (NULL, operands[0], operands[1],
11234                     operands[2], NULL, false);
11235   DONE;
11236 })
11237
11238 (define_expand "sibcall"
11239   [(call (match_operand:QI 0 "" "")
11240          (match_operand 1 "" ""))
11241    (use (match_operand 2 "" ""))]
11242   ""
11243 {
11244   ix86_expand_call (NULL, operands[0], operands[1],
11245                     operands[2], NULL, true);
11246   DONE;
11247 })
11248
11249 (define_insn_and_split "*call_vzeroupper"
11250   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11251          (match_operand 1 "" ""))
11252    (unspec [(match_operand 2 "const_int_operand" "")]
11253            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11254   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11255   "#"
11256   "&& reload_completed"
11257   [(const_int 0)]
11258   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11259   [(set_attr "type" "call")])
11260
11261 (define_insn "*call"
11262   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11263          (match_operand 1 "" ""))]
11264   "!SIBLING_CALL_P (insn)"
11265   "* return ix86_output_call_insn (insn, operands[0]);"
11266   [(set_attr "type" "call")])
11267
11268 (define_insn_and_split "*call_rex64_ms_sysv_vzeroupper"
11269   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11270          (match_operand 1 "" ""))
11271    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11272    (clobber (reg:TI XMM6_REG))
11273    (clobber (reg:TI XMM7_REG))
11274    (clobber (reg:TI XMM8_REG))
11275    (clobber (reg:TI XMM9_REG))
11276    (clobber (reg:TI XMM10_REG))
11277    (clobber (reg:TI XMM11_REG))
11278    (clobber (reg:TI XMM12_REG))
11279    (clobber (reg:TI XMM13_REG))
11280    (clobber (reg:TI XMM14_REG))
11281    (clobber (reg:TI XMM15_REG))
11282    (clobber (reg:DI SI_REG))
11283    (clobber (reg:DI DI_REG))
11284    (unspec [(match_operand 2 "const_int_operand" "")]
11285            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11286   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11287   "#"
11288   "&& reload_completed"
11289   [(const_int 0)]
11290   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11291   [(set_attr "type" "call")])
11292
11293 (define_insn "*call_rex64_ms_sysv"
11294   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11295          (match_operand 1 "" ""))
11296    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11297    (clobber (reg:TI XMM6_REG))
11298    (clobber (reg:TI XMM7_REG))
11299    (clobber (reg:TI XMM8_REG))
11300    (clobber (reg:TI XMM9_REG))
11301    (clobber (reg:TI XMM10_REG))
11302    (clobber (reg:TI XMM11_REG))
11303    (clobber (reg:TI XMM12_REG))
11304    (clobber (reg:TI XMM13_REG))
11305    (clobber (reg:TI XMM14_REG))
11306    (clobber (reg:TI XMM15_REG))
11307    (clobber (reg:DI SI_REG))
11308    (clobber (reg:DI DI_REG))]
11309   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11310   "* return ix86_output_call_insn (insn, operands[0]);"
11311   [(set_attr "type" "call")])
11312
11313 (define_insn_and_split "*sibcall_vzeroupper"
11314   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11315          (match_operand 1 "" ""))
11316    (unspec [(match_operand 2 "const_int_operand" "")]
11317            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11318   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11319   "#"
11320   "&& reload_completed"
11321   [(const_int 0)]
11322   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11323   [(set_attr "type" "call")])
11324
11325 (define_insn "*sibcall"
11326   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11327          (match_operand 1 "" ""))]
11328   "SIBLING_CALL_P (insn)"
11329   "* return ix86_output_call_insn (insn, operands[0]);"
11330   [(set_attr "type" "call")])
11331
11332 (define_expand "call_pop"
11333   [(parallel [(call (match_operand:QI 0 "" "")
11334                     (match_operand:SI 1 "" ""))
11335               (set (reg:SI SP_REG)
11336                    (plus:SI (reg:SI SP_REG)
11337                             (match_operand:SI 3 "" "")))])]
11338   "!TARGET_64BIT"
11339 {
11340   ix86_expand_call (NULL, operands[0], operands[1],
11341                     operands[2], operands[3], false);
11342   DONE;
11343 })
11344
11345 (define_insn_and_split "*call_pop_vzeroupper"
11346   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11347          (match_operand:SI 1 "" ""))
11348    (set (reg:SI SP_REG)
11349         (plus:SI (reg:SI SP_REG)
11350                  (match_operand:SI 2 "immediate_operand" "i")))
11351    (unspec [(match_operand 3 "const_int_operand" "")]
11352            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11353   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11354   "#"
11355   "&& reload_completed"
11356   [(const_int 0)]
11357   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11358   [(set_attr "type" "call")])
11359
11360 (define_insn "*call_pop"
11361   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11362          (match_operand 1 "" ""))
11363    (set (reg:SI SP_REG)
11364         (plus:SI (reg:SI SP_REG)
11365                  (match_operand:SI 2 "immediate_operand" "i")))]
11366   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11367   "* return ix86_output_call_insn (insn, operands[0]);"
11368   [(set_attr "type" "call")])
11369
11370 (define_insn_and_split "*sibcall_pop_vzeroupper"
11371   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11372          (match_operand 1 "" ""))
11373    (set (reg:SI SP_REG)
11374         (plus:SI (reg:SI SP_REG)
11375                  (match_operand:SI 2 "immediate_operand" "i")))
11376    (unspec [(match_operand 3 "const_int_operand" "")]
11377            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11378   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11379   "#"
11380   "&& reload_completed"
11381   [(const_int 0)]
11382   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11383   [(set_attr "type" "call")])
11384
11385 (define_insn "*sibcall_pop"
11386   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11387          (match_operand 1 "" ""))
11388    (set (reg:SI SP_REG)
11389         (plus:SI (reg:SI SP_REG)
11390                  (match_operand:SI 2 "immediate_operand" "i")))]
11391   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11392   "* return ix86_output_call_insn (insn, operands[0]);"
11393   [(set_attr "type" "call")])
11394
11395 ;; Call subroutine, returning value in operand 0
11396
11397 (define_expand "call_value"
11398   [(set (match_operand 0 "" "")
11399         (call (match_operand:QI 1 "" "")
11400               (match_operand 2 "" "")))
11401    (use (match_operand 3 "" ""))]
11402   ""
11403 {
11404   ix86_expand_call (operands[0], operands[1], operands[2],
11405                     operands[3], NULL, false);
11406   DONE;
11407 })
11408
11409 (define_expand "sibcall_value"
11410   [(set (match_operand 0 "" "")
11411         (call (match_operand:QI 1 "" "")
11412               (match_operand 2 "" "")))
11413    (use (match_operand 3 "" ""))]
11414   ""
11415 {
11416   ix86_expand_call (operands[0], operands[1], operands[2],
11417                     operands[3], NULL, true);
11418   DONE;
11419 })
11420
11421 (define_insn_and_split "*call_value_vzeroupper"
11422   [(set (match_operand 0 "" "")
11423         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11424               (match_operand 2 "" "")))
11425    (unspec [(match_operand 3 "const_int_operand" "")]
11426            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11427   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11428   "#"
11429   "&& reload_completed"
11430   [(const_int 0)]
11431   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11432   [(set_attr "type" "callv")])
11433
11434 (define_insn "*call_value"
11435   [(set (match_operand 0 "" "")
11436         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11437               (match_operand 2 "" "")))]
11438   "!SIBLING_CALL_P (insn)"
11439   "* return ix86_output_call_insn (insn, operands[1]);"
11440   [(set_attr "type" "callv")])
11441
11442 (define_insn_and_split "*sibcall_value_vzeroupper"
11443   [(set (match_operand 0 "" "")
11444         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11445               (match_operand 2 "" "")))
11446    (unspec [(match_operand 3 "const_int_operand" "")]
11447            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11448   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11449   "#"
11450   "&& reload_completed"
11451   [(const_int 0)]
11452   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11453   [(set_attr "type" "callv")])
11454
11455 (define_insn "*sibcall_value"
11456   [(set (match_operand 0 "" "")
11457         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11458               (match_operand 2 "" "")))]
11459   "SIBLING_CALL_P (insn)"
11460   "* return ix86_output_call_insn (insn, operands[1]);"
11461   [(set_attr "type" "callv")])
11462
11463 (define_insn_and_split "*call_value_rex64_ms_sysv_vzeroupper"
11464   [(set (match_operand 0 "" "")
11465         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11466               (match_operand 2 "" "")))
11467    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11468    (clobber (reg:TI XMM6_REG))
11469    (clobber (reg:TI XMM7_REG))
11470    (clobber (reg:TI XMM8_REG))
11471    (clobber (reg:TI XMM9_REG))
11472    (clobber (reg:TI XMM10_REG))
11473    (clobber (reg:TI XMM11_REG))
11474    (clobber (reg:TI XMM12_REG))
11475    (clobber (reg:TI XMM13_REG))
11476    (clobber (reg:TI XMM14_REG))
11477    (clobber (reg:TI XMM15_REG))
11478    (clobber (reg:DI SI_REG))
11479    (clobber (reg:DI DI_REG))
11480    (unspec [(match_operand 3 "const_int_operand" "")]
11481            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11482   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11483   "#"
11484   "&& reload_completed"
11485   [(const_int 0)]
11486   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11487   [(set_attr "type" "callv")])
11488
11489 (define_insn "*call_value_rex64_ms_sysv"
11490   [(set (match_operand 0 "" "")
11491         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11492               (match_operand 2 "" "")))
11493    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11494    (clobber (reg:TI XMM6_REG))
11495    (clobber (reg:TI XMM7_REG))
11496    (clobber (reg:TI XMM8_REG))
11497    (clobber (reg:TI XMM9_REG))
11498    (clobber (reg:TI XMM10_REG))
11499    (clobber (reg:TI XMM11_REG))
11500    (clobber (reg:TI XMM12_REG))
11501    (clobber (reg:TI XMM13_REG))
11502    (clobber (reg:TI XMM14_REG))
11503    (clobber (reg:TI XMM15_REG))
11504    (clobber (reg:DI SI_REG))
11505    (clobber (reg:DI DI_REG))]
11506   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11507   "* return ix86_output_call_insn (insn, operands[1]);"
11508   [(set_attr "type" "callv")])
11509
11510 (define_expand "call_value_pop"
11511   [(parallel [(set (match_operand 0 "" "")
11512                    (call (match_operand:QI 1 "" "")
11513                          (match_operand:SI 2 "" "")))
11514               (set (reg:SI SP_REG)
11515                    (plus:SI (reg:SI SP_REG)
11516                             (match_operand:SI 4 "" "")))])]
11517   "!TARGET_64BIT"
11518 {
11519   ix86_expand_call (operands[0], operands[1], operands[2],
11520                     operands[3], operands[4], false);
11521   DONE;
11522 })
11523
11524 (define_insn_and_split "*call_value_pop_vzeroupper"
11525   [(set (match_operand 0 "" "")
11526         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11527               (match_operand 2 "" "")))
11528    (set (reg:SI SP_REG)
11529         (plus:SI (reg:SI SP_REG)
11530                  (match_operand:SI 3 "immediate_operand" "i")))
11531    (unspec [(match_operand 4 "const_int_operand" "")]
11532            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11533   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11534   "#"
11535   "&& reload_completed"
11536   [(const_int 0)]
11537   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11538   [(set_attr "type" "callv")])
11539
11540 (define_insn "*call_value_pop"
11541   [(set (match_operand 0 "" "")
11542         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11543               (match_operand 2 "" "")))
11544    (set (reg:SI SP_REG)
11545         (plus:SI (reg:SI SP_REG)
11546                  (match_operand:SI 3 "immediate_operand" "i")))]
11547   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11548   "* return ix86_output_call_insn (insn, operands[1]);"
11549   [(set_attr "type" "callv")])
11550
11551 (define_insn_and_split "*sibcall_value_pop_vzeroupper"
11552   [(set (match_operand 0 "" "")
11553         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11554               (match_operand 2 "" "")))
11555    (set (reg:SI SP_REG)
11556         (plus:SI (reg:SI SP_REG)
11557                  (match_operand:SI 3 "immediate_operand" "i")))
11558    (unspec [(match_operand 4 "const_int_operand" "")]
11559            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11560   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11561   "#"
11562   "&& reload_completed"
11563   [(const_int 0)]
11564   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11565   [(set_attr "type" "callv")])
11566
11567 (define_insn "*sibcall_value_pop"
11568   [(set (match_operand 0 "" "")
11569         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11570               (match_operand 2 "" "")))
11571    (set (reg:SI SP_REG)
11572         (plus:SI (reg:SI SP_REG)
11573                  (match_operand:SI 3 "immediate_operand" "i")))]
11574   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11575   "* return ix86_output_call_insn (insn, operands[1]);"
11576   [(set_attr "type" "callv")])
11577
11578 ;; Call subroutine returning any type.
11579
11580 (define_expand "untyped_call"
11581   [(parallel [(call (match_operand 0 "" "")
11582                     (const_int 0))
11583               (match_operand 1 "" "")
11584               (match_operand 2 "" "")])]
11585   ""
11586 {
11587   int i;
11588
11589   /* In order to give reg-stack an easier job in validating two
11590      coprocessor registers as containing a possible return value,
11591      simply pretend the untyped call returns a complex long double
11592      value. 
11593
11594      We can't use SSE_REGPARM_MAX here since callee is unprototyped
11595      and should have the default ABI.  */
11596
11597   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
11598                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
11599                     operands[0], const0_rtx,
11600                     GEN_INT ((TARGET_64BIT
11601                               ? (ix86_abi == SYSV_ABI
11602                                  ? X86_64_SSE_REGPARM_MAX
11603                                  : X86_64_MS_SSE_REGPARM_MAX)
11604                               : X86_32_SSE_REGPARM_MAX)
11605                              - 1),
11606                     NULL, false);
11607
11608   for (i = 0; i < XVECLEN (operands[2], 0); i++)
11609     {
11610       rtx set = XVECEXP (operands[2], 0, i);
11611       emit_move_insn (SET_DEST (set), SET_SRC (set));
11612     }
11613
11614   /* The optimizer does not know that the call sets the function value
11615      registers we stored in the result block.  We avoid problems by
11616      claiming that all hard registers are used and clobbered at this
11617      point.  */
11618   emit_insn (gen_blockage ());
11619
11620   DONE;
11621 })
11622 \f
11623 ;; Prologue and epilogue instructions
11624
11625 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
11626 ;; all of memory.  This blocks insns from being moved across this point.
11627
11628 (define_insn "blockage"
11629   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
11630   ""
11631   ""
11632   [(set_attr "length" "0")])
11633
11634 ;; Do not schedule instructions accessing memory across this point.
11635
11636 (define_expand "memory_blockage"
11637   [(set (match_dup 0)
11638         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11639   ""
11640 {
11641   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
11642   MEM_VOLATILE_P (operands[0]) = 1;
11643 })
11644
11645 (define_insn "*memory_blockage"
11646   [(set (match_operand:BLK 0 "" "")
11647         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11648   ""
11649   ""
11650   [(set_attr "length" "0")])
11651
11652 ;; As USE insns aren't meaningful after reload, this is used instead
11653 ;; to prevent deleting instructions setting registers for PIC code
11654 (define_insn "prologue_use"
11655   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
11656   ""
11657   ""
11658   [(set_attr "length" "0")])
11659
11660 ;; Insn emitted into the body of a function to return from a function.
11661 ;; This is only done if the function's epilogue is known to be simple.
11662 ;; See comments for ix86_can_use_return_insn_p in i386.c.
11663
11664 (define_expand "return"
11665   [(simple_return)]
11666   "ix86_can_use_return_insn_p ()"
11667 {
11668   ix86_maybe_emit_epilogue_vzeroupper ();
11669   if (crtl->args.pops_args)
11670     {
11671       rtx popc = GEN_INT (crtl->args.pops_args);
11672       emit_jump_insn (gen_simple_return_pop_internal (popc));
11673       DONE;
11674     }
11675 })
11676
11677 ;; We need to disable this for TARGET_SEH, as otherwise
11678 ;; shrink-wrapped prologue gets enabled too.  This might exceed
11679 ;; the maximum size of prologue in unwind information.
11680
11681 (define_expand "simple_return"
11682   [(simple_return)]
11683   "!TARGET_SEH"
11684 {
11685   ix86_maybe_emit_epilogue_vzeroupper ();
11686   if (crtl->args.pops_args)
11687     {
11688       rtx popc = GEN_INT (crtl->args.pops_args);
11689       emit_jump_insn (gen_simple_return_pop_internal (popc));
11690       DONE;
11691     }
11692 })
11693
11694 (define_insn "simple_return_internal"
11695   [(simple_return)]
11696   "reload_completed"
11697   "ret"
11698   [(set_attr "length" "1")
11699    (set_attr "atom_unit" "jeu")
11700    (set_attr "length_immediate" "0")
11701    (set_attr "modrm" "0")])
11702
11703 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
11704 ;; instruction Athlon and K8 have.
11705
11706 (define_insn "simple_return_internal_long"
11707   [(simple_return)
11708    (unspec [(const_int 0)] UNSPEC_REP)]
11709   "reload_completed"
11710   "rep\;ret"
11711   [(set_attr "length" "2")
11712    (set_attr "atom_unit" "jeu")
11713    (set_attr "length_immediate" "0")
11714    (set_attr "prefix_rep" "1")
11715    (set_attr "modrm" "0")])
11716
11717 (define_insn "simple_return_pop_internal"
11718   [(simple_return)
11719    (use (match_operand:SI 0 "const_int_operand" ""))]
11720   "reload_completed"
11721   "ret\t%0"
11722   [(set_attr "length" "3")
11723    (set_attr "atom_unit" "jeu")
11724    (set_attr "length_immediate" "2")
11725    (set_attr "modrm" "0")])
11726
11727 (define_insn "simple_return_indirect_internal"
11728   [(simple_return)
11729    (use (match_operand:SI 0 "register_operand" "r"))]
11730   "reload_completed"
11731   "jmp\t%A0"
11732   [(set_attr "type" "ibr")
11733    (set_attr "length_immediate" "0")])
11734
11735 (define_insn "nop"
11736   [(const_int 0)]
11737   ""
11738   "nop"
11739   [(set_attr "length" "1")
11740    (set_attr "length_immediate" "0")
11741    (set_attr "modrm" "0")])
11742
11743 ;; Generate nops.  Operand 0 is the number of nops, up to 8.
11744 (define_insn "nops"
11745   [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
11746                     UNSPECV_NOPS)]
11747   "reload_completed"
11748 {
11749   int num = INTVAL (operands[0]);
11750
11751   gcc_assert (num >= 1 && num <= 8);
11752
11753   while (num--)
11754     fputs ("\tnop\n", asm_out_file);
11755
11756   return "";
11757 }
11758   [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))
11759    (set_attr "length_immediate" "0")
11760    (set_attr "modrm" "0")])
11761
11762 ;; Pad to 16-byte boundary, max skip in op0.  Used to avoid
11763 ;; branch prediction penalty for the third jump in a 16-byte
11764 ;; block on K8.
11765
11766 (define_insn "pad"
11767   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
11768   ""
11769 {
11770 #ifdef ASM_OUTPUT_MAX_SKIP_PAD
11771   ASM_OUTPUT_MAX_SKIP_PAD (asm_out_file, 4, (int)INTVAL (operands[0]));
11772 #else
11773   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
11774      The align insn is used to avoid 3 jump instructions in the row to improve
11775      branch prediction and the benefits hardly outweigh the cost of extra 8
11776      nops on the average inserted by full alignment pseudo operation.  */
11777 #endif
11778   return "";
11779 }
11780   [(set_attr "length" "16")])
11781
11782 (define_expand "prologue"
11783   [(const_int 0)]
11784   ""
11785   "ix86_expand_prologue (); DONE;")
11786
11787 (define_insn "set_got"
11788   [(set (match_operand:SI 0 "register_operand" "=r")
11789         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
11790    (clobber (reg:CC FLAGS_REG))]
11791   "!TARGET_64BIT"
11792   "* return output_set_got (operands[0], NULL_RTX);"
11793   [(set_attr "type" "multi")
11794    (set_attr "length" "12")])
11795
11796 (define_insn "set_got_labelled"
11797   [(set (match_operand:SI 0 "register_operand" "=r")
11798         (unspec:SI [(label_ref (match_operand 1 "" ""))]
11799          UNSPEC_SET_GOT))
11800    (clobber (reg:CC FLAGS_REG))]
11801   "!TARGET_64BIT"
11802   "* return output_set_got (operands[0], operands[1]);"
11803   [(set_attr "type" "multi")
11804    (set_attr "length" "12")])
11805
11806 (define_insn "set_got_rex64"
11807   [(set (match_operand:DI 0 "register_operand" "=r")
11808         (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
11809   "TARGET_64BIT"
11810   "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
11811   [(set_attr "type" "lea")
11812    (set_attr "length_address" "4")
11813    (set_attr "mode" "DI")])
11814
11815 (define_insn "set_rip_rex64"
11816   [(set (match_operand:DI 0 "register_operand" "=r")
11817         (unspec:DI [(label_ref (match_operand 1 "" ""))] UNSPEC_SET_RIP))]
11818   "TARGET_64BIT"
11819   "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
11820   [(set_attr "type" "lea")
11821    (set_attr "length_address" "4")
11822    (set_attr "mode" "DI")])
11823
11824 (define_insn "set_got_offset_rex64"
11825   [(set (match_operand:DI 0 "register_operand" "=r")
11826         (unspec:DI
11827           [(label_ref (match_operand 1 "" ""))]
11828           UNSPEC_SET_GOT_OFFSET))]
11829   "TARGET_LP64"
11830   "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
11831   [(set_attr "type" "imov")
11832    (set_attr "length_immediate" "0")
11833    (set_attr "length_address" "8")
11834    (set_attr "mode" "DI")])
11835
11836 (define_expand "epilogue"
11837   [(const_int 0)]
11838   ""
11839   "ix86_expand_epilogue (1); DONE;")
11840
11841 (define_expand "sibcall_epilogue"
11842   [(const_int 0)]
11843   ""
11844   "ix86_expand_epilogue (0); DONE;")
11845
11846 (define_expand "eh_return"
11847   [(use (match_operand 0 "register_operand" ""))]
11848   ""
11849 {
11850   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
11851
11852   /* Tricky bit: we write the address of the handler to which we will
11853      be returning into someone else's stack frame, one word below the
11854      stack address we wish to restore.  */
11855   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
11856   tmp = plus_constant (tmp, -UNITS_PER_WORD);
11857   tmp = gen_rtx_MEM (Pmode, tmp);
11858   emit_move_insn (tmp, ra);
11859
11860   emit_jump_insn (gen_eh_return_internal ());
11861   emit_barrier ();
11862   DONE;
11863 })
11864
11865 (define_insn_and_split "eh_return_internal"
11866   [(eh_return)]
11867   ""
11868   "#"
11869   "epilogue_completed"
11870   [(const_int 0)]
11871   "ix86_expand_epilogue (2); DONE;")
11872
11873 (define_insn "leave"
11874   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
11875    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
11876    (clobber (mem:BLK (scratch)))]
11877   "!TARGET_64BIT"
11878   "leave"
11879   [(set_attr "type" "leave")])
11880
11881 (define_insn "leave_rex64"
11882   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
11883    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
11884    (clobber (mem:BLK (scratch)))]
11885   "TARGET_64BIT"
11886   "leave"
11887   [(set_attr "type" "leave")])
11888 \f
11889 ;; Handle -fsplit-stack.
11890
11891 (define_expand "split_stack_prologue"
11892   [(const_int 0)]
11893   ""
11894 {
11895   ix86_expand_split_stack_prologue ();
11896   DONE;
11897 })
11898
11899 ;; In order to support the call/return predictor, we use a return
11900 ;; instruction which the middle-end doesn't see.
11901 (define_insn "split_stack_return"
11902   [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "")]
11903                      UNSPECV_SPLIT_STACK_RETURN)]
11904   ""
11905 {
11906   if (operands[0] == const0_rtx)
11907     return "ret";
11908   else
11909     return "ret\t%0";
11910 }
11911   [(set_attr "atom_unit" "jeu")
11912    (set_attr "modrm" "0")
11913    (set (attr "length")
11914         (if_then_else (match_operand:SI 0 "const0_operand" "")
11915                       (const_int 1)
11916                       (const_int 3)))
11917    (set (attr "length_immediate")
11918         (if_then_else (match_operand:SI 0 "const0_operand" "")
11919                       (const_int 0)
11920                       (const_int 2)))])
11921
11922 ;; If there are operand 0 bytes available on the stack, jump to
11923 ;; operand 1.
11924
11925 (define_expand "split_stack_space_check"
11926   [(set (pc) (if_then_else
11927               (ltu (minus (reg SP_REG)
11928                           (match_operand 0 "register_operand" ""))
11929                    (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
11930               (label_ref (match_operand 1 "" ""))
11931               (pc)))]
11932   ""
11933 {
11934   rtx reg, size, limit;
11935
11936   reg = gen_reg_rtx (Pmode);
11937   size = force_reg (Pmode, operands[0]);
11938   emit_insn (gen_sub3_insn (reg, stack_pointer_rtx, size));
11939   limit = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx),
11940                           UNSPEC_STACK_CHECK);
11941   limit = gen_rtx_MEM (Pmode, gen_rtx_CONST (Pmode, limit));
11942   ix86_expand_branch (GEU, reg, limit, operands[1]);
11943
11944   DONE;
11945 })
11946 \f
11947 ;; Bit manipulation instructions.
11948
11949 (define_expand "ffs<mode>2"
11950   [(set (match_dup 2) (const_int -1))
11951    (parallel [(set (reg:CCZ FLAGS_REG)
11952                    (compare:CCZ
11953                      (match_operand:SWI48 1 "nonimmediate_operand" "")
11954                      (const_int 0)))
11955               (set (match_operand:SWI48 0 "register_operand" "")
11956                    (ctz:SWI48 (match_dup 1)))])
11957    (set (match_dup 0) (if_then_else:SWI48
11958                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
11959                         (match_dup 2)
11960                         (match_dup 0)))
11961    (parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (const_int 1)))
11962               (clobber (reg:CC FLAGS_REG))])]
11963   ""
11964 {
11965   if (<MODE>mode == SImode && !TARGET_CMOVE)
11966     {
11967       emit_insn (gen_ffssi2_no_cmove (operands[0], operands [1]));
11968       DONE;
11969     }
11970   operands[2] = gen_reg_rtx (<MODE>mode);
11971 })
11972
11973 (define_insn_and_split "ffssi2_no_cmove"
11974   [(set (match_operand:SI 0 "register_operand" "=r")
11975         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
11976    (clobber (match_scratch:SI 2 "=&q"))
11977    (clobber (reg:CC FLAGS_REG))]
11978   "!TARGET_CMOVE"
11979   "#"
11980   "&& reload_completed"
11981   [(parallel [(set (reg:CCZ FLAGS_REG)
11982                    (compare:CCZ (match_dup 1) (const_int 0)))
11983               (set (match_dup 0) (ctz:SI (match_dup 1)))])
11984    (set (strict_low_part (match_dup 3))
11985         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
11986    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
11987               (clobber (reg:CC FLAGS_REG))])
11988    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
11989               (clobber (reg:CC FLAGS_REG))])
11990    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
11991               (clobber (reg:CC FLAGS_REG))])]
11992 {
11993   operands[3] = gen_lowpart (QImode, operands[2]);
11994   ix86_expand_clear (operands[2]);
11995 })
11996
11997 (define_insn "*ffs<mode>_1"
11998   [(set (reg:CCZ FLAGS_REG)
11999         (compare:CCZ (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12000                      (const_int 0)))
12001    (set (match_operand:SWI48 0 "register_operand" "=r")
12002         (ctz:SWI48 (match_dup 1)))]
12003   ""
12004   "bsf{<imodesuffix>}\t{%1, %0|%0, %1}"
12005   [(set_attr "type" "alu1")
12006    (set_attr "prefix_0f" "1")
12007    (set_attr "mode" "<MODE>")])
12008
12009 (define_insn "ctz<mode>2"
12010   [(set (match_operand:SWI248 0 "register_operand" "=r")
12011         (ctz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12012    (clobber (reg:CC FLAGS_REG))]
12013   ""
12014 {
12015   if (TARGET_BMI)
12016     return "tzcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12017   else
12018     return "bsf{<imodesuffix>}\t{%1, %0|%0, %1}";
12019 }
12020   [(set_attr "type" "alu1")
12021    (set_attr "prefix_0f" "1")
12022    (set (attr "prefix_rep") (symbol_ref "TARGET_BMI"))
12023    (set_attr "mode" "<MODE>")])
12024
12025 (define_expand "clz<mode>2"
12026   [(parallel
12027      [(set (match_operand:SWI248 0 "register_operand" "")
12028            (minus:SWI248
12029              (match_dup 2)
12030              (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" ""))))
12031       (clobber (reg:CC FLAGS_REG))])
12032    (parallel
12033      [(set (match_dup 0) (xor:SWI248 (match_dup 0) (match_dup 2)))
12034       (clobber (reg:CC FLAGS_REG))])]
12035   ""
12036 {
12037   if (TARGET_LZCNT)
12038     {
12039       emit_insn (gen_clz<mode>2_lzcnt (operands[0], operands[1]));
12040       DONE;
12041     }
12042   operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
12043 })
12044
12045 (define_insn "clz<mode>2_lzcnt"
12046   [(set (match_operand:SWI248 0 "register_operand" "=r")
12047         (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12048    (clobber (reg:CC FLAGS_REG))]
12049   "TARGET_LZCNT"
12050   "lzcnt{<imodesuffix>}\t{%1, %0|%0, %1}"
12051   [(set_attr "prefix_rep" "1")
12052    (set_attr "type" "bitmanip")
12053    (set_attr "mode" "<MODE>")])
12054
12055 ;; BMI instructions.
12056 (define_insn "*bmi_andn_<mode>"
12057   [(set (match_operand:SWI48 0 "register_operand" "=r")
12058         (and:SWI48
12059           (not:SWI48
12060             (match_operand:SWI48 1 "register_operand" "r"))
12061             (match_operand:SWI48 2 "nonimmediate_operand" "rm")))
12062    (clobber (reg:CC FLAGS_REG))]
12063   "TARGET_BMI"
12064   "andn\t{%2, %1, %0|%0, %1, %2}"
12065   [(set_attr "type" "bitmanip")
12066    (set_attr "mode" "<MODE>")])
12067
12068 (define_insn "bmi_bextr_<mode>"
12069   [(set (match_operand:SWI48 0 "register_operand" "=r")
12070         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12071                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12072                        UNSPEC_BEXTR))
12073    (clobber (reg:CC FLAGS_REG))]
12074   "TARGET_BMI"
12075   "bextr\t{%2, %1, %0|%0, %1, %2}"
12076   [(set_attr "type" "bitmanip")
12077    (set_attr "mode" "<MODE>")])
12078
12079 (define_insn "*bmi_blsi_<mode>"
12080   [(set (match_operand:SWI48 0 "register_operand" "=r")
12081         (and:SWI48
12082           (neg:SWI48
12083             (match_operand:SWI48 1 "nonimmediate_operand" "rm"))
12084           (match_dup 1)))
12085    (clobber (reg:CC FLAGS_REG))]
12086   "TARGET_BMI"
12087   "blsi\t{%1, %0|%0, %1}"
12088   [(set_attr "type" "bitmanip")
12089    (set_attr "mode" "<MODE>")])
12090
12091 (define_insn "*bmi_blsmsk_<mode>"
12092   [(set (match_operand:SWI48 0 "register_operand" "=r")
12093         (xor:SWI48
12094           (plus:SWI48
12095             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12096             (const_int -1))
12097           (match_dup 1)))
12098    (clobber (reg:CC FLAGS_REG))]
12099   "TARGET_BMI"
12100   "blsmsk\t{%1, %0|%0, %1}"
12101   [(set_attr "type" "bitmanip")
12102    (set_attr "mode" "<MODE>")])
12103
12104 (define_insn "*bmi_blsr_<mode>"
12105   [(set (match_operand:SWI48 0 "register_operand" "=r")
12106         (and:SWI48
12107           (plus:SWI48
12108             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12109             (const_int -1))
12110           (match_dup 1)))
12111    (clobber (reg:CC FLAGS_REG))]
12112    "TARGET_BMI"
12113    "blsr\t{%1, %0|%0, %1}"
12114   [(set_attr "type" "bitmanip")
12115    (set_attr "mode" "<MODE>")])
12116
12117 ;; BMI2 instructions.
12118 (define_insn "bmi2_bzhi_<mode>3"
12119   [(set (match_operand:SWI48 0 "register_operand" "=r")
12120         (and:SWI48 (match_operand:SWI48 1 "register_operand" "r")
12121                    (lshiftrt:SWI48 (const_int -1)
12122                                    (match_operand:SWI48 2 "nonimmediate_operand" "rm"))))
12123    (clobber (reg:CC FLAGS_REG))]
12124   "TARGET_BMI2"
12125   "bzhi\t{%2, %1, %0|%0, %1, %2}"
12126   [(set_attr "type" "bitmanip")
12127    (set_attr "prefix" "vex")
12128    (set_attr "mode" "<MODE>")])
12129
12130 (define_insn "bmi2_pdep_<mode>3"
12131   [(set (match_operand:SWI48 0 "register_operand" "=r")
12132         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12133                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12134                        UNSPEC_PDEP))]
12135   "TARGET_BMI2"
12136   "pdep\t{%2, %1, %0|%0, %1, %2}"
12137   [(set_attr "type" "bitmanip")
12138    (set_attr "prefix" "vex")
12139    (set_attr "mode" "<MODE>")])
12140
12141 (define_insn "bmi2_pext_<mode>3"
12142   [(set (match_operand:SWI48 0 "register_operand" "=r")
12143         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12144                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12145                        UNSPEC_PEXT))]
12146   "TARGET_BMI2"
12147   "pext\t{%2, %1, %0|%0, %1, %2}"
12148   [(set_attr "type" "bitmanip")
12149    (set_attr "prefix" "vex")
12150    (set_attr "mode" "<MODE>")])
12151
12152 ;; TBM instructions.
12153 (define_insn "tbm_bextri_<mode>"
12154   [(set (match_operand:SWI48 0 "register_operand" "=r")
12155         (zero_extract:SWI48
12156           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12157           (match_operand:SWI48 2 "const_0_to_255_operand" "n")
12158           (match_operand:SWI48 3 "const_0_to_255_operand" "n")))
12159    (clobber (reg:CC FLAGS_REG))]
12160    "TARGET_TBM"
12161 {
12162   operands[2] = GEN_INT (INTVAL (operands[2]) << 8 | INTVAL (operands[3]));
12163   return "bextr\t{%2, %1, %0|%0, %1, %2}";
12164 }
12165   [(set_attr "type" "bitmanip")
12166    (set_attr "mode" "<MODE>")])
12167
12168 (define_insn "*tbm_blcfill_<mode>"
12169   [(set (match_operand:SWI48 0 "register_operand" "=r")
12170         (and:SWI48
12171           (plus:SWI48
12172             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12173             (const_int 1))
12174           (match_dup 1)))
12175    (clobber (reg:CC FLAGS_REG))]
12176    "TARGET_TBM"
12177    "blcfill\t{%1, %0|%0, %1}"
12178   [(set_attr "type" "bitmanip")
12179    (set_attr "mode" "<MODE>")])
12180
12181 (define_insn "*tbm_blci_<mode>"
12182   [(set (match_operand:SWI48 0 "register_operand" "=r")
12183         (ior:SWI48
12184           (not:SWI48
12185             (plus:SWI48
12186               (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12187               (const_int 1)))
12188           (match_dup 1)))
12189    (clobber (reg:CC FLAGS_REG))]
12190    "TARGET_TBM"
12191    "blci\t{%1, %0|%0, %1}"
12192   [(set_attr "type" "bitmanip")
12193    (set_attr "mode" "<MODE>")])
12194
12195 (define_insn "*tbm_blcic_<mode>"
12196   [(set (match_operand:SWI48 0 "register_operand" "=r")
12197         (and:SWI48
12198           (plus:SWI48
12199             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12200             (const_int 1))
12201           (not:SWI48
12202             (match_dup 1))))
12203    (clobber (reg:CC FLAGS_REG))]
12204    "TARGET_TBM"
12205    "blcic\t{%1, %0|%0, %1}"
12206   [(set_attr "type" "bitmanip")
12207    (set_attr "mode" "<MODE>")])
12208
12209 (define_insn "*tbm_blcmsk_<mode>"
12210   [(set (match_operand:SWI48 0 "register_operand" "=r")
12211         (xor:SWI48
12212           (plus:SWI48
12213             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12214             (const_int 1))
12215           (match_dup 1)))
12216    (clobber (reg:CC FLAGS_REG))]
12217    "TARGET_TBM"
12218    "blcmsk\t{%1, %0|%0, %1}"
12219   [(set_attr "type" "bitmanip")
12220    (set_attr "mode" "<MODE>")])
12221
12222 (define_insn "*tbm_blcs_<mode>"
12223   [(set (match_operand:SWI48 0 "register_operand" "=r")
12224         (ior:SWI48
12225           (plus:SWI48
12226             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12227             (const_int 1))
12228           (match_dup 1)))
12229    (clobber (reg:CC FLAGS_REG))]
12230    "TARGET_TBM"
12231    "blcs\t{%1, %0|%0, %1}"
12232   [(set_attr "type" "bitmanip")
12233    (set_attr "mode" "<MODE>")])
12234
12235 (define_insn "*tbm_blsfill_<mode>"
12236   [(set (match_operand:SWI48 0 "register_operand" "=r")
12237         (ior:SWI48
12238           (plus:SWI48
12239             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12240             (const_int -1))
12241           (match_dup 1)))
12242    (clobber (reg:CC FLAGS_REG))]
12243    "TARGET_TBM"
12244    "blsfill\t{%1, %0|%0, %1}"
12245   [(set_attr "type" "bitmanip")
12246    (set_attr "mode" "<MODE>")])
12247
12248 (define_insn "*tbm_blsic_<mode>"
12249   [(set (match_operand:SWI48 0 "register_operand" "=r")
12250         (ior:SWI48
12251           (plus:SWI48
12252             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12253             (const_int -1))
12254           (not:SWI48
12255             (match_dup 1))))
12256    (clobber (reg:CC FLAGS_REG))]
12257    "TARGET_TBM"
12258    "blsic\t{%1, %0|%0, %1}"
12259   [(set_attr "type" "bitmanip")
12260    (set_attr "mode" "<MODE>")])
12261
12262 (define_insn "*tbm_t1mskc_<mode>"
12263   [(set (match_operand:SWI48 0 "register_operand" "=r")
12264         (ior:SWI48
12265           (plus:SWI48
12266             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12267             (const_int 1))
12268           (not:SWI48
12269             (match_dup 1))))
12270    (clobber (reg:CC FLAGS_REG))]
12271    "TARGET_TBM"
12272    "t1mskc\t{%1, %0|%0, %1}"
12273   [(set_attr "type" "bitmanip")
12274    (set_attr "mode" "<MODE>")])
12275
12276 (define_insn "*tbm_tzmsk_<mode>"
12277   [(set (match_operand:SWI48 0 "register_operand" "=r")
12278         (and:SWI48
12279           (plus:SWI48
12280             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12281             (const_int -1))
12282           (not:SWI48
12283             (match_dup 1))))
12284    (clobber (reg:CC FLAGS_REG))]
12285    "TARGET_TBM"
12286    "tzmsk\t{%1, %0|%0, %1}"
12287   [(set_attr "type" "bitmanip")
12288    (set_attr "mode" "<MODE>")])
12289
12290 (define_insn "bsr_rex64"
12291   [(set (match_operand:DI 0 "register_operand" "=r")
12292         (minus:DI (const_int 63)
12293                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
12294    (clobber (reg:CC FLAGS_REG))]
12295   "TARGET_64BIT"
12296   "bsr{q}\t{%1, %0|%0, %1}"
12297   [(set_attr "type" "alu1")
12298    (set_attr "prefix_0f" "1")
12299    (set_attr "mode" "DI")])
12300
12301 (define_insn "bsr"
12302   [(set (match_operand:SI 0 "register_operand" "=r")
12303         (minus:SI (const_int 31)
12304                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
12305    (clobber (reg:CC FLAGS_REG))]
12306   ""
12307   "bsr{l}\t{%1, %0|%0, %1}"
12308   [(set_attr "type" "alu1")
12309    (set_attr "prefix_0f" "1")
12310    (set_attr "mode" "SI")])
12311
12312 (define_insn "*bsrhi"
12313   [(set (match_operand:HI 0 "register_operand" "=r")
12314         (minus:HI (const_int 15)
12315                   (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
12316    (clobber (reg:CC FLAGS_REG))]
12317   ""
12318   "bsr{w}\t{%1, %0|%0, %1}"
12319   [(set_attr "type" "alu1")
12320    (set_attr "prefix_0f" "1")
12321    (set_attr "mode" "HI")])
12322
12323 (define_insn "popcount<mode>2"
12324   [(set (match_operand:SWI248 0 "register_operand" "=r")
12325         (popcount:SWI248
12326           (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12327    (clobber (reg:CC FLAGS_REG))]
12328   "TARGET_POPCNT"
12329 {
12330 #if TARGET_MACHO
12331   return "popcnt\t{%1, %0|%0, %1}";
12332 #else
12333   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12334 #endif
12335 }
12336   [(set_attr "prefix_rep" "1")
12337    (set_attr "type" "bitmanip")
12338    (set_attr "mode" "<MODE>")])
12339
12340 (define_insn "*popcount<mode>2_cmp"
12341   [(set (reg FLAGS_REG)
12342         (compare
12343           (popcount:SWI248
12344             (match_operand:SWI248 1 "nonimmediate_operand" "rm"))
12345           (const_int 0)))
12346    (set (match_operand:SWI248 0 "register_operand" "=r")
12347         (popcount:SWI248 (match_dup 1)))]
12348   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12349 {
12350 #if TARGET_MACHO
12351   return "popcnt\t{%1, %0|%0, %1}";
12352 #else
12353   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12354 #endif
12355 }
12356   [(set_attr "prefix_rep" "1")
12357    (set_attr "type" "bitmanip")
12358    (set_attr "mode" "<MODE>")])
12359
12360 (define_insn "*popcountsi2_cmp_zext"
12361   [(set (reg FLAGS_REG)
12362         (compare
12363           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
12364           (const_int 0)))
12365    (set (match_operand:DI 0 "register_operand" "=r")
12366         (zero_extend:DI(popcount:SI (match_dup 1))))]
12367   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12368 {
12369 #if TARGET_MACHO
12370   return "popcnt\t{%1, %0|%0, %1}";
12371 #else
12372   return "popcnt{l}\t{%1, %0|%0, %1}";
12373 #endif
12374 }
12375   [(set_attr "prefix_rep" "1")
12376    (set_attr "type" "bitmanip")
12377    (set_attr "mode" "SI")])
12378
12379 (define_expand "bswap<mode>2"
12380   [(set (match_operand:SWI48 0 "register_operand" "")
12381         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "")))]
12382   ""
12383 {
12384   if (<MODE>mode == SImode && !(TARGET_BSWAP || TARGET_MOVBE))
12385     {
12386       rtx x = operands[0];
12387
12388       emit_move_insn (x, operands[1]);
12389       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12390       emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
12391       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12392       DONE;
12393     }
12394 })
12395
12396 (define_insn "*bswap<mode>2_movbe"
12397   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,r,m")
12398         (bswap:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,m,r")))]
12399   "TARGET_MOVBE
12400    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12401   "@
12402     bswap\t%0
12403     movbe\t{%1, %0|%0, %1}
12404     movbe\t{%1, %0|%0, %1}"
12405   [(set_attr "type" "bitmanip,imov,imov")
12406    (set_attr "modrm" "0,1,1")
12407    (set_attr "prefix_0f" "*,1,1")
12408    (set_attr "prefix_extra" "*,1,1")
12409    (set_attr "mode" "<MODE>")])
12410
12411 (define_insn "*bswap<mode>2_1"
12412   [(set (match_operand:SWI48 0 "register_operand" "=r")
12413         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "0")))]
12414   "TARGET_BSWAP"
12415   "bswap\t%0"
12416   [(set_attr "type" "bitmanip")
12417    (set_attr "modrm" "0")
12418    (set_attr "mode" "<MODE>")])
12419
12420 (define_insn "*bswaphi_lowpart_1"
12421   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
12422         (bswap:HI (match_dup 0)))
12423    (clobber (reg:CC FLAGS_REG))]
12424   "TARGET_USE_XCHGB || optimize_function_for_size_p (cfun)"
12425   "@
12426     xchg{b}\t{%h0, %b0|%b0, %h0}
12427     rol{w}\t{$8, %0|%0, 8}"
12428   [(set_attr "length" "2,4")
12429    (set_attr "mode" "QI,HI")])
12430
12431 (define_insn "bswaphi_lowpart"
12432   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
12433         (bswap:HI (match_dup 0)))
12434    (clobber (reg:CC FLAGS_REG))]
12435   ""
12436   "rol{w}\t{$8, %0|%0, 8}"
12437   [(set_attr "length" "4")
12438    (set_attr "mode" "HI")])
12439
12440 (define_expand "paritydi2"
12441   [(set (match_operand:DI 0 "register_operand" "")
12442         (parity:DI (match_operand:DI 1 "register_operand" "")))]
12443   "! TARGET_POPCNT"
12444 {
12445   rtx scratch = gen_reg_rtx (QImode);
12446   rtx cond;
12447
12448   emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
12449                                 NULL_RTX, operands[1]));
12450
12451   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12452                          gen_rtx_REG (CCmode, FLAGS_REG),
12453                          const0_rtx);
12454   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12455
12456   if (TARGET_64BIT)
12457     emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
12458   else
12459     {
12460       rtx tmp = gen_reg_rtx (SImode);
12461
12462       emit_insn (gen_zero_extendqisi2 (tmp, scratch));
12463       emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
12464     }
12465   DONE;
12466 })
12467
12468 (define_expand "paritysi2"
12469   [(set (match_operand:SI 0 "register_operand" "")
12470         (parity:SI (match_operand:SI 1 "register_operand" "")))]
12471   "! TARGET_POPCNT"
12472 {
12473   rtx scratch = gen_reg_rtx (QImode);
12474   rtx cond;
12475
12476   emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
12477
12478   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12479                          gen_rtx_REG (CCmode, FLAGS_REG),
12480                          const0_rtx);
12481   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12482
12483   emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
12484   DONE;
12485 })
12486
12487 (define_insn_and_split "paritydi2_cmp"
12488   [(set (reg:CC FLAGS_REG)
12489         (unspec:CC [(match_operand:DI 3 "register_operand" "0")]
12490                    UNSPEC_PARITY))
12491    (clobber (match_scratch:DI 0 "=r"))
12492    (clobber (match_scratch:SI 1 "=&r"))
12493    (clobber (match_scratch:HI 2 "=Q"))]
12494   "! TARGET_POPCNT"
12495   "#"
12496   "&& reload_completed"
12497   [(parallel
12498      [(set (match_dup 1)
12499            (xor:SI (match_dup 1) (match_dup 4)))
12500       (clobber (reg:CC FLAGS_REG))])
12501    (parallel
12502      [(set (reg:CC FLAGS_REG)
12503            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12504       (clobber (match_dup 1))
12505       (clobber (match_dup 2))])]
12506 {
12507   operands[4] = gen_lowpart (SImode, operands[3]);
12508
12509   if (TARGET_64BIT)
12510     {
12511       emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
12512       emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
12513     }
12514   else
12515     operands[1] = gen_highpart (SImode, operands[3]);
12516 })
12517
12518 (define_insn_and_split "paritysi2_cmp"
12519   [(set (reg:CC FLAGS_REG)
12520         (unspec:CC [(match_operand:SI 2 "register_operand" "0")]
12521                    UNSPEC_PARITY))
12522    (clobber (match_scratch:SI 0 "=r"))
12523    (clobber (match_scratch:HI 1 "=&Q"))]
12524   "! TARGET_POPCNT"
12525   "#"
12526   "&& reload_completed"
12527   [(parallel
12528      [(set (match_dup 1)
12529            (xor:HI (match_dup 1) (match_dup 3)))
12530       (clobber (reg:CC FLAGS_REG))])
12531    (parallel
12532      [(set (reg:CC FLAGS_REG)
12533            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12534       (clobber (match_dup 1))])]
12535 {
12536   operands[3] = gen_lowpart (HImode, operands[2]);
12537
12538   emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
12539   emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
12540 })
12541
12542 (define_insn "*parityhi2_cmp"
12543   [(set (reg:CC FLAGS_REG)
12544         (unspec:CC [(match_operand:HI 1 "register_operand" "0")]
12545                    UNSPEC_PARITY))
12546    (clobber (match_scratch:HI 0 "=Q"))]
12547   "! TARGET_POPCNT"
12548   "xor{b}\t{%h0, %b0|%b0, %h0}"
12549   [(set_attr "length" "2")
12550    (set_attr "mode" "HI")])
12551
12552 \f
12553 ;; Thread-local storage patterns for ELF.
12554 ;;
12555 ;; Note that these code sequences must appear exactly as shown
12556 ;; in order to allow linker relaxation.
12557
12558 (define_insn "*tls_global_dynamic_32_gnu"
12559   [(set (match_operand:SI 0 "register_operand" "=a")
12560         (unspec:SI
12561          [(match_operand:SI 1 "register_operand" "b")
12562           (match_operand:SI 2 "tls_symbolic_operand" "")
12563           (match_operand:SI 3 "constant_call_address_operand" "z")]
12564          UNSPEC_TLS_GD))
12565    (clobber (match_scratch:SI 4 "=d"))
12566    (clobber (match_scratch:SI 5 "=c"))
12567    (clobber (reg:CC FLAGS_REG))]
12568   "!TARGET_64BIT && TARGET_GNU_TLS"
12569 {
12570   output_asm_insn
12571     ("lea{l}\t{%E2@tlsgd(,%1,1), %0|%0, %E2@tlsgd[%1*1]}", operands);
12572   if (TARGET_SUN_TLS)
12573 #ifdef HAVE_AS_IX86_TLSGDPLT
12574     return "call\t%a2@tlsgdplt";
12575 #else
12576     return "call\t%p3@plt";
12577 #endif
12578   return "call\t%P3";
12579 }
12580   [(set_attr "type" "multi")
12581    (set_attr "length" "12")])
12582
12583 (define_expand "tls_global_dynamic_32"
12584   [(parallel
12585     [(set (match_operand:SI 0 "register_operand" "")
12586           (unspec:SI [(match_operand:SI 2 "register_operand" "")
12587                       (match_operand:SI 1 "tls_symbolic_operand" "")
12588                       (match_operand:SI 3 "constant_call_address_operand" "")]
12589                      UNSPEC_TLS_GD))
12590      (clobber (match_scratch:SI 4 ""))
12591      (clobber (match_scratch:SI 5 ""))
12592      (clobber (reg:CC FLAGS_REG))])])
12593
12594 (define_insn "*tls_global_dynamic_64"
12595   [(set (match_operand:DI 0 "register_operand" "=a")
12596         (call:DI
12597          (mem:QI (match_operand:DI 2 "constant_call_address_operand" "z"))
12598          (match_operand:DI 3 "" "")))
12599    (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12600               UNSPEC_TLS_GD)]
12601   "TARGET_64BIT"
12602 {
12603   if (!TARGET_X32)
12604     fputs (ASM_BYTE "0x66\n", asm_out_file);
12605   output_asm_insn
12606     ("lea{q}\t{%E1@tlsgd(%%rip), %%rdi|rdi, %E1@tlsgd[rip]}", operands);
12607   fputs (ASM_SHORT "0x6666\n", asm_out_file);
12608   fputs ("\trex64\n", asm_out_file);
12609   if (TARGET_SUN_TLS)
12610     return "call\t%p2@plt";
12611   return "call\t%P2";
12612 }
12613   [(set_attr "type" "multi")
12614    (set (attr "length")
12615         (symbol_ref "TARGET_X32 ? 15 : 16"))])
12616
12617 (define_expand "tls_global_dynamic_64"
12618   [(parallel
12619     [(set (match_operand:DI 0 "register_operand" "")
12620           (call:DI
12621            (mem:QI (match_operand:DI 2 "constant_call_address_operand" ""))
12622            (const_int 0)))
12623      (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12624                 UNSPEC_TLS_GD)])])
12625
12626 (define_insn "*tls_local_dynamic_base_32_gnu"
12627   [(set (match_operand:SI 0 "register_operand" "=a")
12628         (unspec:SI
12629          [(match_operand:SI 1 "register_operand" "b")
12630           (match_operand:SI 2 "constant_call_address_operand" "z")]
12631          UNSPEC_TLS_LD_BASE))
12632    (clobber (match_scratch:SI 3 "=d"))
12633    (clobber (match_scratch:SI 4 "=c"))
12634    (clobber (reg:CC FLAGS_REG))]
12635   "!TARGET_64BIT && TARGET_GNU_TLS"
12636 {
12637   output_asm_insn
12638     ("lea{l}\t{%&@tlsldm(%1), %0|%0, %&@tlsldm[%1]}", operands);
12639   if (TARGET_SUN_TLS)
12640 #ifdef HAVE_AS_IX86_TLSLDMPLT
12641     return "call\t%&@tlsldmplt";
12642 #else
12643     return "call\t%p2@plt";
12644 #endif
12645   return "call\t%P2";
12646 }
12647   [(set_attr "type" "multi")
12648    (set_attr "length" "11")])
12649
12650 (define_expand "tls_local_dynamic_base_32"
12651   [(parallel
12652      [(set (match_operand:SI 0 "register_operand" "")
12653            (unspec:SI
12654             [(match_operand:SI 1 "register_operand" "")
12655              (match_operand:SI 2 "constant_call_address_operand" "")]
12656             UNSPEC_TLS_LD_BASE))
12657       (clobber (match_scratch:SI 3 ""))
12658       (clobber (match_scratch:SI 4 ""))
12659       (clobber (reg:CC FLAGS_REG))])])
12660
12661 (define_insn "*tls_local_dynamic_base_64"
12662   [(set (match_operand:DI 0 "register_operand" "=a")
12663         (call:DI
12664          (mem:QI (match_operand:DI 1 "constant_call_address_operand" "z"))
12665          (match_operand:DI 2 "" "")))
12666    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
12667   "TARGET_64BIT"
12668 {
12669   output_asm_insn
12670     ("lea{q}\t{%&@tlsld(%%rip), %%rdi|rdi, %&@tlsld[rip]}", operands);
12671   if (TARGET_SUN_TLS)
12672     return "call\t%p1@plt";
12673   return "call\t%P1";
12674 }
12675   [(set_attr "type" "multi")
12676    (set_attr "length" "12")])
12677
12678 (define_expand "tls_local_dynamic_base_64"
12679   [(parallel
12680      [(set (match_operand:DI 0 "register_operand" "")
12681            (call:DI
12682             (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
12683             (const_int 0)))
12684       (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])])
12685
12686 ;; Local dynamic of a single variable is a lose.  Show combine how
12687 ;; to convert that back to global dynamic.
12688
12689 (define_insn_and_split "*tls_local_dynamic_32_once"
12690   [(set (match_operand:SI 0 "register_operand" "=a")
12691         (plus:SI
12692          (unspec:SI [(match_operand:SI 1 "register_operand" "b")
12693                      (match_operand:SI 2 "constant_call_address_operand" "z")]
12694                     UNSPEC_TLS_LD_BASE)
12695          (const:SI (unspec:SI
12696                     [(match_operand:SI 3 "tls_symbolic_operand" "")]
12697                     UNSPEC_DTPOFF))))
12698    (clobber (match_scratch:SI 4 "=d"))
12699    (clobber (match_scratch:SI 5 "=c"))
12700    (clobber (reg:CC FLAGS_REG))]
12701   ""
12702   "#"
12703   ""
12704   [(parallel
12705      [(set (match_dup 0)
12706            (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
12707                       UNSPEC_TLS_GD))
12708       (clobber (match_dup 4))
12709       (clobber (match_dup 5))
12710       (clobber (reg:CC FLAGS_REG))])])
12711
12712 ;; Segment register for the thread base ptr load
12713 (define_mode_attr tp_seg [(SI "gs") (DI "fs")])
12714
12715 ;; Load and add the thread base pointer from %<tp_seg>:0.
12716 (define_insn "*load_tp_x32"
12717   [(set (match_operand:SI 0 "register_operand" "=r")
12718         (unspec:SI [(const_int 0)] UNSPEC_TP))]
12719   "TARGET_X32"
12720   "mov{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12721   [(set_attr "type" "imov")
12722    (set_attr "modrm" "0")
12723    (set_attr "length" "7")
12724    (set_attr "memory" "load")
12725    (set_attr "imm_disp" "false")])
12726
12727 (define_insn "*load_tp_x32_zext"
12728   [(set (match_operand:DI 0 "register_operand" "=r")
12729         (zero_extend:DI (unspec:SI [(const_int 0)] UNSPEC_TP)))]
12730   "TARGET_X32"
12731   "mov{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12732   [(set_attr "type" "imov")
12733    (set_attr "modrm" "0")
12734    (set_attr "length" "7")
12735    (set_attr "memory" "load")
12736    (set_attr "imm_disp" "false")])
12737
12738 (define_insn "*load_tp_<mode>"
12739   [(set (match_operand:P 0 "register_operand" "=r")
12740         (unspec:P [(const_int 0)] UNSPEC_TP))]
12741   "!TARGET_X32"
12742   "mov{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12743   [(set_attr "type" "imov")
12744    (set_attr "modrm" "0")
12745    (set_attr "length" "7")
12746    (set_attr "memory" "load")
12747    (set_attr "imm_disp" "false")])
12748
12749 (define_insn "*add_tp_x32"
12750   [(set (match_operand:SI 0 "register_operand" "=r")
12751         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12752                  (match_operand:SI 1 "register_operand" "0")))
12753    (clobber (reg:CC FLAGS_REG))]
12754   "TARGET_X32"
12755   "add{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12756   [(set_attr "type" "alu")
12757    (set_attr "modrm" "0")
12758    (set_attr "length" "7")
12759    (set_attr "memory" "load")
12760    (set_attr "imm_disp" "false")])
12761
12762 (define_insn "*add_tp_x32_zext"
12763   [(set (match_operand:DI 0 "register_operand" "=r")
12764         (zero_extend:DI
12765           (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12766                    (match_operand:SI 1 "register_operand" "0"))))
12767    (clobber (reg:CC FLAGS_REG))]
12768   "TARGET_X32"
12769   "add{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12770   [(set_attr "type" "alu")
12771    (set_attr "modrm" "0")
12772    (set_attr "length" "7")
12773    (set_attr "memory" "load")
12774    (set_attr "imm_disp" "false")])
12775
12776 (define_insn "*add_tp_<mode>"
12777   [(set (match_operand:P 0 "register_operand" "=r")
12778         (plus:P (unspec:P [(const_int 0)] UNSPEC_TP)
12779                 (match_operand:P 1 "register_operand" "0")))
12780    (clobber (reg:CC FLAGS_REG))]
12781   "!TARGET_X32"
12782   "add{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12783   [(set_attr "type" "alu")
12784    (set_attr "modrm" "0")
12785    (set_attr "length" "7")
12786    (set_attr "memory" "load")
12787    (set_attr "imm_disp" "false")])
12788
12789 ;; The Sun linker took the AMD64 TLS spec literally and can only handle
12790 ;; %rax as destination of the initial executable code sequence.
12791 (define_insn "tls_initial_exec_64_sun"
12792   [(set (match_operand:DI 0 "register_operand" "=a")
12793         (unspec:DI
12794          [(match_operand:DI 1 "tls_symbolic_operand" "")]
12795          UNSPEC_TLS_IE_SUN))
12796    (clobber (reg:CC FLAGS_REG))]
12797   "TARGET_64BIT && TARGET_SUN_TLS"
12798 {
12799   output_asm_insn
12800     ("mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}", operands);
12801   return "add{q}\t{%a1@gottpoff(%%rip), %0|%0, %a1@gottpoff[rip]}";
12802 }
12803   [(set_attr "type" "multi")])
12804
12805 ;; GNU2 TLS patterns can be split.
12806
12807 (define_expand "tls_dynamic_gnu2_32"
12808   [(set (match_dup 3)
12809         (plus:SI (match_operand:SI 2 "register_operand" "")
12810                  (const:SI
12811                   (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
12812                              UNSPEC_TLSDESC))))
12813    (parallel
12814     [(set (match_operand:SI 0 "register_operand" "")
12815           (unspec:SI [(match_dup 1) (match_dup 3)
12816                       (match_dup 2) (reg:SI SP_REG)]
12817                       UNSPEC_TLSDESC))
12818      (clobber (reg:CC FLAGS_REG))])]
12819   "!TARGET_64BIT && TARGET_GNU2_TLS"
12820 {
12821   operands[3] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12822   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12823 })
12824
12825 (define_insn "*tls_dynamic_gnu2_lea_32"
12826   [(set (match_operand:SI 0 "register_operand" "=r")
12827         (plus:SI (match_operand:SI 1 "register_operand" "b")
12828                  (const:SI
12829                   (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
12830                               UNSPEC_TLSDESC))))]
12831   "!TARGET_64BIT && TARGET_GNU2_TLS"
12832   "lea{l}\t{%E2@TLSDESC(%1), %0|%0, %E2@TLSDESC[%1]}"
12833   [(set_attr "type" "lea")
12834    (set_attr "mode" "SI")
12835    (set_attr "length" "6")
12836    (set_attr "length_address" "4")])
12837
12838 (define_insn "*tls_dynamic_gnu2_call_32"
12839   [(set (match_operand:SI 0 "register_operand" "=a")
12840         (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
12841                     (match_operand:SI 2 "register_operand" "0")
12842                     ;; we have to make sure %ebx still points to the GOT
12843                     (match_operand:SI 3 "register_operand" "b")
12844                     (reg:SI SP_REG)]
12845                    UNSPEC_TLSDESC))
12846    (clobber (reg:CC FLAGS_REG))]
12847   "!TARGET_64BIT && TARGET_GNU2_TLS"
12848   "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
12849   [(set_attr "type" "call")
12850    (set_attr "length" "2")
12851    (set_attr "length_address" "0")])
12852
12853 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
12854   [(set (match_operand:SI 0 "register_operand" "=&a")
12855         (plus:SI
12856          (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
12857                      (match_operand:SI 4 "" "")
12858                      (match_operand:SI 2 "register_operand" "b")
12859                      (reg:SI SP_REG)]
12860                     UNSPEC_TLSDESC)
12861          (const:SI (unspec:SI
12862                     [(match_operand:SI 1 "tls_symbolic_operand" "")]
12863                     UNSPEC_DTPOFF))))
12864    (clobber (reg:CC FLAGS_REG))]
12865   "!TARGET_64BIT && TARGET_GNU2_TLS"
12866   "#"
12867   ""
12868   [(set (match_dup 0) (match_dup 5))]
12869 {
12870   operands[5] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12871   emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
12872 })
12873
12874 (define_expand "tls_dynamic_gnu2_64"
12875   [(set (match_dup 2)
12876         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12877                    UNSPEC_TLSDESC))
12878    (parallel
12879     [(set (match_operand:DI 0 "register_operand" "")
12880           (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
12881                      UNSPEC_TLSDESC))
12882      (clobber (reg:CC FLAGS_REG))])]
12883   "TARGET_64BIT && TARGET_GNU2_TLS"
12884 {
12885   operands[2] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12886   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12887 })
12888
12889 (define_insn "*tls_dynamic_gnu2_lea_64"
12890   [(set (match_operand:DI 0 "register_operand" "=r")
12891         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12892                    UNSPEC_TLSDESC))]
12893   "TARGET_64BIT && TARGET_GNU2_TLS"
12894   "lea{q}\t{%E1@TLSDESC(%%rip), %0|%0, %E1@TLSDESC[rip]}"
12895   [(set_attr "type" "lea")
12896    (set_attr "mode" "DI")
12897    (set_attr "length" "7")
12898    (set_attr "length_address" "4")])
12899
12900 (define_insn "*tls_dynamic_gnu2_call_64"
12901   [(set (match_operand:DI 0 "register_operand" "=a")
12902         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")
12903                     (match_operand:DI 2 "register_operand" "0")
12904                     (reg:DI SP_REG)]
12905                    UNSPEC_TLSDESC))
12906    (clobber (reg:CC FLAGS_REG))]
12907   "TARGET_64BIT && TARGET_GNU2_TLS"
12908   "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
12909   [(set_attr "type" "call")
12910    (set_attr "length" "2")
12911    (set_attr "length_address" "0")])
12912
12913 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
12914   [(set (match_operand:DI 0 "register_operand" "=&a")
12915         (plus:DI
12916          (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
12917                      (match_operand:DI 3 "" "")
12918                      (reg:DI SP_REG)]
12919                     UNSPEC_TLSDESC)
12920          (const:DI (unspec:DI
12921                     [(match_operand 1 "tls_symbolic_operand" "")]
12922                     UNSPEC_DTPOFF))))
12923    (clobber (reg:CC FLAGS_REG))]
12924   "TARGET_64BIT && TARGET_GNU2_TLS"
12925   "#"
12926   ""
12927   [(set (match_dup 0) (match_dup 4))]
12928 {
12929   operands[4] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12930   emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
12931 })
12932 \f
12933 ;; These patterns match the binary 387 instructions for addM3, subM3,
12934 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
12935 ;; SFmode.  The first is the normal insn, the second the same insn but
12936 ;; with one operand a conversion, and the third the same insn but with
12937 ;; the other operand a conversion.  The conversion may be SFmode or
12938 ;; SImode if the target mode DFmode, but only SImode if the target mode
12939 ;; is SFmode.
12940
12941 ;; Gcc is slightly more smart about handling normal two address instructions
12942 ;; so use special patterns for add and mull.
12943
12944 (define_insn "*fop_<mode>_comm_mixed"
12945   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
12946         (match_operator:MODEF 3 "binary_fp_operator"
12947           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,0,x")
12948            (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm,xm")]))]
12949   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
12950    && COMMUTATIVE_ARITH_P (operands[3])
12951    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12952   "* return output_387_binary_op (insn, operands);"
12953   [(set (attr "type")
12954         (if_then_else (eq_attr "alternative" "1,2")
12955            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12956               (const_string "ssemul")
12957               (const_string "sseadd"))
12958            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12959               (const_string "fmul")
12960               (const_string "fop"))))
12961    (set_attr "isa" "*,noavx,avx")
12962    (set_attr "prefix" "orig,orig,vex")
12963    (set_attr "mode" "<MODE>")])
12964
12965 (define_insn "*fop_<mode>_comm_sse"
12966   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
12967         (match_operator:MODEF 3 "binary_fp_operator"
12968           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
12969            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
12970   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
12971    && COMMUTATIVE_ARITH_P (operands[3])
12972    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12973   "* return output_387_binary_op (insn, operands);"
12974   [(set (attr "type")
12975         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12976            (const_string "ssemul")
12977            (const_string "sseadd")))
12978    (set_attr "isa" "noavx,avx")
12979    (set_attr "prefix" "orig,vex")
12980    (set_attr "mode" "<MODE>")])
12981
12982 (define_insn "*fop_<mode>_comm_i387"
12983   [(set (match_operand:MODEF 0 "register_operand" "=f")
12984         (match_operator:MODEF 3 "binary_fp_operator"
12985           [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
12986            (match_operand:MODEF 2 "nonimmediate_operand" "fm")]))]
12987   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
12988    && COMMUTATIVE_ARITH_P (operands[3])
12989    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12990   "* return output_387_binary_op (insn, operands);"
12991   [(set (attr "type")
12992         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12993            (const_string "fmul")
12994            (const_string "fop")))
12995    (set_attr "mode" "<MODE>")])
12996
12997 (define_insn "*fop_<mode>_1_mixed"
12998   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
12999         (match_operator:MODEF 3 "binary_fp_operator"
13000           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,0,x")
13001            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm,xm")]))]
13002   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
13003    && !COMMUTATIVE_ARITH_P (operands[3])
13004    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13005   "* return output_387_binary_op (insn, operands);"
13006   [(set (attr "type")
13007         (cond [(and (eq_attr "alternative" "2,3")
13008                     (match_operand:MODEF 3 "mult_operator" ""))
13009                  (const_string "ssemul")
13010                (and (eq_attr "alternative" "2,3")
13011                     (match_operand:MODEF 3 "div_operator" ""))
13012                  (const_string "ssediv")
13013                (eq_attr "alternative" "2,3")
13014                  (const_string "sseadd")
13015                (match_operand:MODEF 3 "mult_operator" "")
13016                  (const_string "fmul")
13017                (match_operand:MODEF 3 "div_operator" "")
13018                  (const_string "fdiv")
13019               ]
13020               (const_string "fop")))
13021    (set_attr "isa" "*,*,noavx,avx")
13022    (set_attr "prefix" "orig,orig,orig,vex")
13023    (set_attr "mode" "<MODE>")])
13024
13025 (define_insn "*rcpsf2_sse"
13026   [(set (match_operand:SF 0 "register_operand" "=x")
13027         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13028                    UNSPEC_RCP))]
13029   "TARGET_SSE_MATH"
13030   "%vrcpss\t{%1, %d0|%d0, %1}"
13031   [(set_attr "type" "sse")
13032    (set_attr "atom_sse_attr" "rcp")
13033    (set_attr "prefix" "maybe_vex")
13034    (set_attr "mode" "SF")])
13035
13036 (define_insn "*fop_<mode>_1_sse"
13037   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
13038         (match_operator:MODEF 3 "binary_fp_operator"
13039           [(match_operand:MODEF 1 "register_operand" "0,x")
13040            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
13041   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13042    && !COMMUTATIVE_ARITH_P (operands[3])"
13043   "* return output_387_binary_op (insn, operands);"
13044   [(set (attr "type")
13045         (cond [(match_operand:MODEF 3 "mult_operator" "")
13046                  (const_string "ssemul")
13047                (match_operand:MODEF 3 "div_operator" "")
13048                  (const_string "ssediv")
13049               ]
13050               (const_string "sseadd")))
13051    (set_attr "isa" "noavx,avx")
13052    (set_attr "prefix" "orig,vex")
13053    (set_attr "mode" "<MODE>")])
13054
13055 ;; This pattern is not fully shadowed by the pattern above.
13056 (define_insn "*fop_<mode>_1_i387"
13057   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13058         (match_operator:MODEF 3 "binary_fp_operator"
13059           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm")
13060            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0")]))]
13061   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
13062    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13063    && !COMMUTATIVE_ARITH_P (operands[3])
13064    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13065   "* return output_387_binary_op (insn, operands);"
13066   [(set (attr "type")
13067         (cond [(match_operand:MODEF 3 "mult_operator" "")
13068                  (const_string "fmul")
13069                (match_operand:MODEF 3 "div_operator" "")
13070                  (const_string "fdiv")
13071               ]
13072               (const_string "fop")))
13073    (set_attr "mode" "<MODE>")])
13074
13075 ;; ??? Add SSE splitters for these!
13076 (define_insn "*fop_<MODEF:mode>_2_i387"
13077   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13078         (match_operator:MODEF 3 "binary_fp_operator"
13079           [(float:MODEF
13080              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13081            (match_operand:MODEF 2 "register_operand" "0,0")]))]
13082   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13083    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13084    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13085   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13086   [(set (attr "type")
13087         (cond [(match_operand:MODEF 3 "mult_operator" "")
13088                  (const_string "fmul")
13089                (match_operand:MODEF 3 "div_operator" "")
13090                  (const_string "fdiv")
13091               ]
13092               (const_string "fop")))
13093    (set_attr "fp_int_src" "true")
13094    (set_attr "mode" "<SWI24:MODE>")])
13095
13096 (define_insn "*fop_<MODEF:mode>_3_i387"
13097   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13098         (match_operator:MODEF 3 "binary_fp_operator"
13099           [(match_operand:MODEF 1 "register_operand" "0,0")
13100            (float:MODEF
13101              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13102   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13103    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13104    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13105   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13106   [(set (attr "type")
13107         (cond [(match_operand:MODEF 3 "mult_operator" "")
13108                  (const_string "fmul")
13109                (match_operand:MODEF 3 "div_operator" "")
13110                  (const_string "fdiv")
13111               ]
13112               (const_string "fop")))
13113    (set_attr "fp_int_src" "true")
13114    (set_attr "mode" "<MODE>")])
13115
13116 (define_insn "*fop_df_4_i387"
13117   [(set (match_operand:DF 0 "register_operand" "=f,f")
13118         (match_operator:DF 3 "binary_fp_operator"
13119            [(float_extend:DF
13120              (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
13121             (match_operand:DF 2 "register_operand" "0,f")]))]
13122   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13123    && !(TARGET_SSE2 && TARGET_SSE_MATH)
13124    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13125   "* return output_387_binary_op (insn, operands);"
13126   [(set (attr "type")
13127         (cond [(match_operand:DF 3 "mult_operator" "")
13128                  (const_string "fmul")
13129                (match_operand:DF 3 "div_operator" "")
13130                  (const_string "fdiv")
13131               ]
13132               (const_string "fop")))
13133    (set_attr "mode" "SF")])
13134
13135 (define_insn "*fop_df_5_i387"
13136   [(set (match_operand:DF 0 "register_operand" "=f,f")
13137         (match_operator:DF 3 "binary_fp_operator"
13138           [(match_operand:DF 1 "register_operand" "0,f")
13139            (float_extend:DF
13140             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13141   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13142    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13143   "* return output_387_binary_op (insn, operands);"
13144   [(set (attr "type")
13145         (cond [(match_operand:DF 3 "mult_operator" "")
13146                  (const_string "fmul")
13147                (match_operand:DF 3 "div_operator" "")
13148                  (const_string "fdiv")
13149               ]
13150               (const_string "fop")))
13151    (set_attr "mode" "SF")])
13152
13153 (define_insn "*fop_df_6_i387"
13154   [(set (match_operand:DF 0 "register_operand" "=f,f")
13155         (match_operator:DF 3 "binary_fp_operator"
13156           [(float_extend:DF
13157             (match_operand:SF 1 "register_operand" "0,f"))
13158            (float_extend:DF
13159             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13160   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13161    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13162   "* return output_387_binary_op (insn, operands);"
13163   [(set (attr "type")
13164         (cond [(match_operand:DF 3 "mult_operator" "")
13165                  (const_string "fmul")
13166                (match_operand:DF 3 "div_operator" "")
13167                  (const_string "fdiv")
13168               ]
13169               (const_string "fop")))
13170    (set_attr "mode" "SF")])
13171
13172 (define_insn "*fop_xf_comm_i387"
13173   [(set (match_operand:XF 0 "register_operand" "=f")
13174         (match_operator:XF 3 "binary_fp_operator"
13175                         [(match_operand:XF 1 "register_operand" "%0")
13176                          (match_operand:XF 2 "register_operand" "f")]))]
13177   "TARGET_80387
13178    && COMMUTATIVE_ARITH_P (operands[3])"
13179   "* return output_387_binary_op (insn, operands);"
13180   [(set (attr "type")
13181         (if_then_else (match_operand:XF 3 "mult_operator" "")
13182            (const_string "fmul")
13183            (const_string "fop")))
13184    (set_attr "mode" "XF")])
13185
13186 (define_insn "*fop_xf_1_i387"
13187   [(set (match_operand:XF 0 "register_operand" "=f,f")
13188         (match_operator:XF 3 "binary_fp_operator"
13189                         [(match_operand:XF 1 "register_operand" "0,f")
13190                          (match_operand:XF 2 "register_operand" "f,0")]))]
13191   "TARGET_80387
13192    && !COMMUTATIVE_ARITH_P (operands[3])"
13193   "* return output_387_binary_op (insn, operands);"
13194   [(set (attr "type")
13195         (cond [(match_operand:XF 3 "mult_operator" "")
13196                  (const_string "fmul")
13197                (match_operand:XF 3 "div_operator" "")
13198                  (const_string "fdiv")
13199               ]
13200               (const_string "fop")))
13201    (set_attr "mode" "XF")])
13202
13203 (define_insn "*fop_xf_2_i387"
13204   [(set (match_operand:XF 0 "register_operand" "=f,f")
13205         (match_operator:XF 3 "binary_fp_operator"
13206           [(float:XF
13207              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13208            (match_operand:XF 2 "register_operand" "0,0")]))]
13209   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13210   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13211   [(set (attr "type")
13212         (cond [(match_operand:XF 3 "mult_operator" "")
13213                  (const_string "fmul")
13214                (match_operand:XF 3 "div_operator" "")
13215                  (const_string "fdiv")
13216               ]
13217               (const_string "fop")))
13218    (set_attr "fp_int_src" "true")
13219    (set_attr "mode" "<MODE>")])
13220
13221 (define_insn "*fop_xf_3_i387"
13222   [(set (match_operand:XF 0 "register_operand" "=f,f")
13223         (match_operator:XF 3 "binary_fp_operator"
13224           [(match_operand:XF 1 "register_operand" "0,0")
13225            (float:XF
13226              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13227   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13228   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13229   [(set (attr "type")
13230         (cond [(match_operand:XF 3 "mult_operator" "")
13231                  (const_string "fmul")
13232                (match_operand:XF 3 "div_operator" "")
13233                  (const_string "fdiv")
13234               ]
13235               (const_string "fop")))
13236    (set_attr "fp_int_src" "true")
13237    (set_attr "mode" "<MODE>")])
13238
13239 (define_insn "*fop_xf_4_i387"
13240   [(set (match_operand:XF 0 "register_operand" "=f,f")
13241         (match_operator:XF 3 "binary_fp_operator"
13242            [(float_extend:XF
13243               (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
13244             (match_operand:XF 2 "register_operand" "0,f")]))]
13245   "TARGET_80387"
13246   "* return output_387_binary_op (insn, operands);"
13247   [(set (attr "type")
13248         (cond [(match_operand:XF 3 "mult_operator" "")
13249                  (const_string "fmul")
13250                (match_operand:XF 3 "div_operator" "")
13251                  (const_string "fdiv")
13252               ]
13253               (const_string "fop")))
13254    (set_attr "mode" "<MODE>")])
13255
13256 (define_insn "*fop_xf_5_i387"
13257   [(set (match_operand:XF 0 "register_operand" "=f,f")
13258         (match_operator:XF 3 "binary_fp_operator"
13259           [(match_operand:XF 1 "register_operand" "0,f")
13260            (float_extend:XF
13261              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13262   "TARGET_80387"
13263   "* return output_387_binary_op (insn, operands);"
13264   [(set (attr "type")
13265         (cond [(match_operand:XF 3 "mult_operator" "")
13266                  (const_string "fmul")
13267                (match_operand:XF 3 "div_operator" "")
13268                  (const_string "fdiv")
13269               ]
13270               (const_string "fop")))
13271    (set_attr "mode" "<MODE>")])
13272
13273 (define_insn "*fop_xf_6_i387"
13274   [(set (match_operand:XF 0 "register_operand" "=f,f")
13275         (match_operator:XF 3 "binary_fp_operator"
13276           [(float_extend:XF
13277              (match_operand:MODEF 1 "register_operand" "0,f"))
13278            (float_extend:XF
13279              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13280   "TARGET_80387"
13281   "* return output_387_binary_op (insn, operands);"
13282   [(set (attr "type")
13283         (cond [(match_operand:XF 3 "mult_operator" "")
13284                  (const_string "fmul")
13285                (match_operand:XF 3 "div_operator" "")
13286                  (const_string "fdiv")
13287               ]
13288               (const_string "fop")))
13289    (set_attr "mode" "<MODE>")])
13290
13291 (define_split
13292   [(set (match_operand 0 "register_operand" "")
13293         (match_operator 3 "binary_fp_operator"
13294            [(float (match_operand:SWI24 1 "register_operand" ""))
13295             (match_operand 2 "register_operand" "")]))]
13296   "reload_completed
13297    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13298    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[1]))"
13299   [(const_int 0)]
13300 {
13301   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
13302   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13303   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13304                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13305                                           GET_MODE (operands[3]),
13306                                           operands[4],
13307                                           operands[2])));
13308   ix86_free_from_memory (GET_MODE (operands[1]));
13309   DONE;
13310 })
13311
13312 (define_split
13313   [(set (match_operand 0 "register_operand" "")
13314         (match_operator 3 "binary_fp_operator"
13315            [(match_operand 1 "register_operand" "")
13316             (float (match_operand:SWI24 2 "register_operand" ""))]))]
13317   "reload_completed
13318    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13319    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[2]))"
13320   [(const_int 0)]
13321 {
13322   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13323   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13324   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13325                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13326                                           GET_MODE (operands[3]),
13327                                           operands[1],
13328                                           operands[4])));
13329   ix86_free_from_memory (GET_MODE (operands[2]));
13330   DONE;
13331 })
13332 \f
13333 ;; FPU special functions.
13334
13335 ;; This pattern implements a no-op XFmode truncation for
13336 ;; all fancy i386 XFmode math functions.
13337
13338 (define_insn "truncxf<mode>2_i387_noop_unspec"
13339   [(set (match_operand:MODEF 0 "register_operand" "=f")
13340         (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
13341         UNSPEC_TRUNC_NOOP))]
13342   "TARGET_USE_FANCY_MATH_387"
13343   "* return output_387_reg_move (insn, operands);"
13344   [(set_attr "type" "fmov")
13345    (set_attr "mode" "<MODE>")])
13346
13347 (define_insn "sqrtxf2"
13348   [(set (match_operand:XF 0 "register_operand" "=f")
13349         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
13350   "TARGET_USE_FANCY_MATH_387"
13351   "fsqrt"
13352   [(set_attr "type" "fpspc")
13353    (set_attr "mode" "XF")
13354    (set_attr "athlon_decode" "direct")
13355    (set_attr "amdfam10_decode" "direct")
13356    (set_attr "bdver1_decode" "direct")])
13357
13358 (define_insn "sqrt_extend<mode>xf2_i387"
13359   [(set (match_operand:XF 0 "register_operand" "=f")
13360         (sqrt:XF
13361           (float_extend:XF
13362             (match_operand:MODEF 1 "register_operand" "0"))))]
13363   "TARGET_USE_FANCY_MATH_387"
13364   "fsqrt"
13365   [(set_attr "type" "fpspc")
13366    (set_attr "mode" "XF")
13367    (set_attr "athlon_decode" "direct")
13368    (set_attr "amdfam10_decode" "direct")
13369    (set_attr "bdver1_decode" "direct")])
13370
13371 (define_insn "*rsqrtsf2_sse"
13372   [(set (match_operand:SF 0 "register_operand" "=x")
13373         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13374                    UNSPEC_RSQRT))]
13375   "TARGET_SSE_MATH"
13376   "%vrsqrtss\t{%1, %d0|%d0, %1}"
13377   [(set_attr "type" "sse")
13378    (set_attr "atom_sse_attr" "rcp")
13379    (set_attr "prefix" "maybe_vex")
13380    (set_attr "mode" "SF")])
13381
13382 (define_expand "rsqrtsf2"
13383   [(set (match_operand:SF 0 "register_operand" "")
13384         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
13385                    UNSPEC_RSQRT))]
13386   "TARGET_SSE_MATH"
13387 {
13388   ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
13389   DONE;
13390 })
13391
13392 (define_insn "*sqrt<mode>2_sse"
13393   [(set (match_operand:MODEF 0 "register_operand" "=x")
13394         (sqrt:MODEF
13395           (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
13396   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
13397   "%vsqrt<ssemodesuffix>\t{%1, %d0|%d0, %1}"
13398   [(set_attr "type" "sse")
13399    (set_attr "atom_sse_attr" "sqrt")
13400    (set_attr "prefix" "maybe_vex")
13401    (set_attr "mode" "<MODE>")
13402    (set_attr "athlon_decode" "*")
13403    (set_attr "amdfam10_decode" "*")
13404    (set_attr "bdver1_decode" "*")])
13405
13406 (define_expand "sqrt<mode>2"
13407   [(set (match_operand:MODEF 0 "register_operand" "")
13408         (sqrt:MODEF
13409           (match_operand:MODEF 1 "nonimmediate_operand" "")))]
13410   "(TARGET_USE_FANCY_MATH_387 && X87_ENABLE_ARITH (<MODE>mode))
13411    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
13412 {
13413   if (<MODE>mode == SFmode
13414       && TARGET_SSE_MATH
13415       && TARGET_RECIP_SQRT
13416       && !optimize_function_for_size_p (cfun)
13417       && flag_finite_math_only && !flag_trapping_math
13418       && flag_unsafe_math_optimizations)
13419     {
13420       ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
13421       DONE;
13422     }
13423
13424   if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
13425     {
13426       rtx op0 = gen_reg_rtx (XFmode);
13427       rtx op1 = force_reg (<MODE>mode, operands[1]);
13428
13429       emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
13430       emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
13431       DONE;
13432    }
13433 })
13434
13435 (define_insn "fpremxf4_i387"
13436   [(set (match_operand:XF 0 "register_operand" "=f")
13437         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13438                     (match_operand:XF 3 "register_operand" "1")]
13439                    UNSPEC_FPREM_F))
13440    (set (match_operand:XF 1 "register_operand" "=u")
13441         (unspec:XF [(match_dup 2) (match_dup 3)]
13442                    UNSPEC_FPREM_U))
13443    (set (reg:CCFP FPSR_REG)
13444         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13445                      UNSPEC_C2_FLAG))]
13446   "TARGET_USE_FANCY_MATH_387"
13447   "fprem"
13448   [(set_attr "type" "fpspc")
13449    (set_attr "mode" "XF")])
13450
13451 (define_expand "fmodxf3"
13452   [(use (match_operand:XF 0 "register_operand" ""))
13453    (use (match_operand:XF 1 "general_operand" ""))
13454    (use (match_operand:XF 2 "general_operand" ""))]
13455   "TARGET_USE_FANCY_MATH_387"
13456 {
13457   rtx label = gen_label_rtx ();
13458
13459   rtx op1 = gen_reg_rtx (XFmode);
13460   rtx op2 = gen_reg_rtx (XFmode);
13461
13462   emit_move_insn (op2, operands[2]);
13463   emit_move_insn (op1, operands[1]);
13464
13465   emit_label (label);
13466   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13467   ix86_emit_fp_unordered_jump (label);
13468   LABEL_NUSES (label) = 1;
13469
13470   emit_move_insn (operands[0], op1);
13471   DONE;
13472 })
13473
13474 (define_expand "fmod<mode>3"
13475   [(use (match_operand:MODEF 0 "register_operand" ""))
13476    (use (match_operand:MODEF 1 "general_operand" ""))
13477    (use (match_operand:MODEF 2 "general_operand" ""))]
13478   "TARGET_USE_FANCY_MATH_387"
13479 {
13480   rtx (*gen_truncxf) (rtx, rtx);
13481
13482   rtx label = gen_label_rtx ();
13483
13484   rtx op1 = gen_reg_rtx (XFmode);
13485   rtx op2 = gen_reg_rtx (XFmode);
13486
13487   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13488   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13489
13490   emit_label (label);
13491   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13492   ix86_emit_fp_unordered_jump (label);
13493   LABEL_NUSES (label) = 1;
13494
13495   /* Truncate the result properly for strict SSE math.  */
13496   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13497       && !TARGET_MIX_SSE_I387)
13498     gen_truncxf = gen_truncxf<mode>2;
13499   else
13500     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13501
13502   emit_insn (gen_truncxf (operands[0], op1));
13503   DONE;
13504 })
13505
13506 (define_insn "fprem1xf4_i387"
13507   [(set (match_operand:XF 0 "register_operand" "=f")
13508         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13509                     (match_operand:XF 3 "register_operand" "1")]
13510                    UNSPEC_FPREM1_F))
13511    (set (match_operand:XF 1 "register_operand" "=u")
13512         (unspec:XF [(match_dup 2) (match_dup 3)]
13513                    UNSPEC_FPREM1_U))
13514    (set (reg:CCFP FPSR_REG)
13515         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13516                      UNSPEC_C2_FLAG))]
13517   "TARGET_USE_FANCY_MATH_387"
13518   "fprem1"
13519   [(set_attr "type" "fpspc")
13520    (set_attr "mode" "XF")])
13521
13522 (define_expand "remainderxf3"
13523   [(use (match_operand:XF 0 "register_operand" ""))
13524    (use (match_operand:XF 1 "general_operand" ""))
13525    (use (match_operand:XF 2 "general_operand" ""))]
13526   "TARGET_USE_FANCY_MATH_387"
13527 {
13528   rtx label = gen_label_rtx ();
13529
13530   rtx op1 = gen_reg_rtx (XFmode);
13531   rtx op2 = gen_reg_rtx (XFmode);
13532
13533   emit_move_insn (op2, operands[2]);
13534   emit_move_insn (op1, operands[1]);
13535
13536   emit_label (label);
13537   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13538   ix86_emit_fp_unordered_jump (label);
13539   LABEL_NUSES (label) = 1;
13540
13541   emit_move_insn (operands[0], op1);
13542   DONE;
13543 })
13544
13545 (define_expand "remainder<mode>3"
13546   [(use (match_operand:MODEF 0 "register_operand" ""))
13547    (use (match_operand:MODEF 1 "general_operand" ""))
13548    (use (match_operand:MODEF 2 "general_operand" ""))]
13549   "TARGET_USE_FANCY_MATH_387"
13550 {
13551   rtx (*gen_truncxf) (rtx, rtx);
13552
13553   rtx label = gen_label_rtx ();
13554
13555   rtx op1 = gen_reg_rtx (XFmode);
13556   rtx op2 = gen_reg_rtx (XFmode);
13557
13558   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13559   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13560
13561   emit_label (label);
13562
13563   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13564   ix86_emit_fp_unordered_jump (label);
13565   LABEL_NUSES (label) = 1;
13566
13567   /* Truncate the result properly for strict SSE math.  */
13568   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13569       && !TARGET_MIX_SSE_I387)
13570     gen_truncxf = gen_truncxf<mode>2;
13571   else
13572     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13573
13574   emit_insn (gen_truncxf (operands[0], op1));
13575   DONE;
13576 })
13577
13578 (define_insn "*sinxf2_i387"
13579   [(set (match_operand:XF 0 "register_operand" "=f")
13580         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
13581   "TARGET_USE_FANCY_MATH_387
13582    && flag_unsafe_math_optimizations"
13583   "fsin"
13584   [(set_attr "type" "fpspc")
13585    (set_attr "mode" "XF")])
13586
13587 (define_insn "*sin_extend<mode>xf2_i387"
13588   [(set (match_operand:XF 0 "register_operand" "=f")
13589         (unspec:XF [(float_extend:XF
13590                       (match_operand:MODEF 1 "register_operand" "0"))]
13591                    UNSPEC_SIN))]
13592   "TARGET_USE_FANCY_MATH_387
13593    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13594        || TARGET_MIX_SSE_I387)
13595    && flag_unsafe_math_optimizations"
13596   "fsin"
13597   [(set_attr "type" "fpspc")
13598    (set_attr "mode" "XF")])
13599
13600 (define_insn "*cosxf2_i387"
13601   [(set (match_operand:XF 0 "register_operand" "=f")
13602         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
13603   "TARGET_USE_FANCY_MATH_387
13604    && flag_unsafe_math_optimizations"
13605   "fcos"
13606   [(set_attr "type" "fpspc")
13607    (set_attr "mode" "XF")])
13608
13609 (define_insn "*cos_extend<mode>xf2_i387"
13610   [(set (match_operand:XF 0 "register_operand" "=f")
13611         (unspec:XF [(float_extend:XF
13612                       (match_operand:MODEF 1 "register_operand" "0"))]
13613                    UNSPEC_COS))]
13614   "TARGET_USE_FANCY_MATH_387
13615    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13616        || TARGET_MIX_SSE_I387)
13617    && flag_unsafe_math_optimizations"
13618   "fcos"
13619   [(set_attr "type" "fpspc")
13620    (set_attr "mode" "XF")])
13621
13622 ;; When sincos pattern is defined, sin and cos builtin functions will be
13623 ;; expanded to sincos pattern with one of its outputs left unused.
13624 ;; CSE pass will figure out if two sincos patterns can be combined,
13625 ;; otherwise sincos pattern will be split back to sin or cos pattern,
13626 ;; depending on the unused output.
13627
13628 (define_insn "sincosxf3"
13629   [(set (match_operand:XF 0 "register_operand" "=f")
13630         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13631                    UNSPEC_SINCOS_COS))
13632    (set (match_operand:XF 1 "register_operand" "=u")
13633         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13634   "TARGET_USE_FANCY_MATH_387
13635    && flag_unsafe_math_optimizations"
13636   "fsincos"
13637   [(set_attr "type" "fpspc")
13638    (set_attr "mode" "XF")])
13639
13640 (define_split
13641   [(set (match_operand:XF 0 "register_operand" "")
13642         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13643                    UNSPEC_SINCOS_COS))
13644    (set (match_operand:XF 1 "register_operand" "")
13645         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13646   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
13647    && can_create_pseudo_p ()"
13648   [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))])
13649
13650 (define_split
13651   [(set (match_operand:XF 0 "register_operand" "")
13652         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13653                    UNSPEC_SINCOS_COS))
13654    (set (match_operand:XF 1 "register_operand" "")
13655         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13656   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13657    && can_create_pseudo_p ()"
13658   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))])
13659
13660 (define_insn "sincos_extend<mode>xf3_i387"
13661   [(set (match_operand:XF 0 "register_operand" "=f")
13662         (unspec:XF [(float_extend:XF
13663                       (match_operand:MODEF 2 "register_operand" "0"))]
13664                    UNSPEC_SINCOS_COS))
13665    (set (match_operand:XF 1 "register_operand" "=u")
13666         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13667   "TARGET_USE_FANCY_MATH_387
13668    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13669        || TARGET_MIX_SSE_I387)
13670    && flag_unsafe_math_optimizations"
13671   "fsincos"
13672   [(set_attr "type" "fpspc")
13673    (set_attr "mode" "XF")])
13674
13675 (define_split
13676   [(set (match_operand:XF 0 "register_operand" "")
13677         (unspec:XF [(float_extend:XF
13678                       (match_operand:MODEF 2 "register_operand" ""))]
13679                    UNSPEC_SINCOS_COS))
13680    (set (match_operand:XF 1 "register_operand" "")
13681         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13682   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
13683    && can_create_pseudo_p ()"
13684   [(set (match_dup 1)
13685         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))])
13686
13687 (define_split
13688   [(set (match_operand:XF 0 "register_operand" "")
13689         (unspec:XF [(float_extend:XF
13690                       (match_operand:MODEF 2 "register_operand" ""))]
13691                    UNSPEC_SINCOS_COS))
13692    (set (match_operand:XF 1 "register_operand" "")
13693         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13694   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13695    && can_create_pseudo_p ()"
13696   [(set (match_dup 0)
13697         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))])
13698
13699 (define_expand "sincos<mode>3"
13700   [(use (match_operand:MODEF 0 "register_operand" ""))
13701    (use (match_operand:MODEF 1 "register_operand" ""))
13702    (use (match_operand:MODEF 2 "register_operand" ""))]
13703   "TARGET_USE_FANCY_MATH_387
13704    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13705        || TARGET_MIX_SSE_I387)
13706    && flag_unsafe_math_optimizations"
13707 {
13708   rtx op0 = gen_reg_rtx (XFmode);
13709   rtx op1 = gen_reg_rtx (XFmode);
13710
13711   emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
13712   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13713   emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
13714   DONE;
13715 })
13716
13717 (define_insn "fptanxf4_i387"
13718   [(set (match_operand:XF 0 "register_operand" "=f")
13719         (match_operand:XF 3 "const_double_operand" "F"))
13720    (set (match_operand:XF 1 "register_operand" "=u")
13721         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13722                    UNSPEC_TAN))]
13723   "TARGET_USE_FANCY_MATH_387
13724    && flag_unsafe_math_optimizations
13725    && standard_80387_constant_p (operands[3]) == 2"
13726   "fptan"
13727   [(set_attr "type" "fpspc")
13728    (set_attr "mode" "XF")])
13729
13730 (define_insn "fptan_extend<mode>xf4_i387"
13731   [(set (match_operand:MODEF 0 "register_operand" "=f")
13732         (match_operand:MODEF 3 "const_double_operand" "F"))
13733    (set (match_operand:XF 1 "register_operand" "=u")
13734         (unspec:XF [(float_extend:XF
13735                       (match_operand:MODEF 2 "register_operand" "0"))]
13736                    UNSPEC_TAN))]
13737   "TARGET_USE_FANCY_MATH_387
13738    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13739        || TARGET_MIX_SSE_I387)
13740    && flag_unsafe_math_optimizations
13741    && standard_80387_constant_p (operands[3]) == 2"
13742   "fptan"
13743   [(set_attr "type" "fpspc")
13744    (set_attr "mode" "XF")])
13745
13746 (define_expand "tanxf2"
13747   [(use (match_operand:XF 0 "register_operand" ""))
13748    (use (match_operand:XF 1 "register_operand" ""))]
13749   "TARGET_USE_FANCY_MATH_387
13750    && flag_unsafe_math_optimizations"
13751 {
13752   rtx one = gen_reg_rtx (XFmode);
13753   rtx op2 = CONST1_RTX (XFmode); /* fld1 */
13754
13755   emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
13756   DONE;
13757 })
13758
13759 (define_expand "tan<mode>2"
13760   [(use (match_operand:MODEF 0 "register_operand" ""))
13761    (use (match_operand:MODEF 1 "register_operand" ""))]
13762   "TARGET_USE_FANCY_MATH_387
13763    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13764        || TARGET_MIX_SSE_I387)
13765    && flag_unsafe_math_optimizations"
13766 {
13767   rtx op0 = gen_reg_rtx (XFmode);
13768
13769   rtx one = gen_reg_rtx (<MODE>mode);
13770   rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
13771
13772   emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
13773                                              operands[1], op2));
13774   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13775   DONE;
13776 })
13777
13778 (define_insn "*fpatanxf3_i387"
13779   [(set (match_operand:XF 0 "register_operand" "=f")
13780         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13781                     (match_operand:XF 2 "register_operand" "u")]
13782                    UNSPEC_FPATAN))
13783    (clobber (match_scratch:XF 3 "=2"))]
13784   "TARGET_USE_FANCY_MATH_387
13785    && flag_unsafe_math_optimizations"
13786   "fpatan"
13787   [(set_attr "type" "fpspc")
13788    (set_attr "mode" "XF")])
13789
13790 (define_insn "fpatan_extend<mode>xf3_i387"
13791   [(set (match_operand:XF 0 "register_operand" "=f")
13792         (unspec:XF [(float_extend:XF
13793                       (match_operand:MODEF 1 "register_operand" "0"))
13794                     (float_extend:XF
13795                       (match_operand:MODEF 2 "register_operand" "u"))]
13796                    UNSPEC_FPATAN))
13797    (clobber (match_scratch:XF 3 "=2"))]
13798   "TARGET_USE_FANCY_MATH_387
13799    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13800        || TARGET_MIX_SSE_I387)
13801    && flag_unsafe_math_optimizations"
13802   "fpatan"
13803   [(set_attr "type" "fpspc")
13804    (set_attr "mode" "XF")])
13805
13806 (define_expand "atan2xf3"
13807   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13808                    (unspec:XF [(match_operand:XF 2 "register_operand" "")
13809                                (match_operand:XF 1 "register_operand" "")]
13810                               UNSPEC_FPATAN))
13811               (clobber (match_scratch:XF 3 ""))])]
13812   "TARGET_USE_FANCY_MATH_387
13813    && flag_unsafe_math_optimizations")
13814
13815 (define_expand "atan2<mode>3"
13816   [(use (match_operand:MODEF 0 "register_operand" ""))
13817    (use (match_operand:MODEF 1 "register_operand" ""))
13818    (use (match_operand:MODEF 2 "register_operand" ""))]
13819   "TARGET_USE_FANCY_MATH_387
13820    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13821        || TARGET_MIX_SSE_I387)
13822    && flag_unsafe_math_optimizations"
13823 {
13824   rtx op0 = gen_reg_rtx (XFmode);
13825
13826   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
13827   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13828   DONE;
13829 })
13830
13831 (define_expand "atanxf2"
13832   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13833                    (unspec:XF [(match_dup 2)
13834                                (match_operand:XF 1 "register_operand" "")]
13835                               UNSPEC_FPATAN))
13836               (clobber (match_scratch:XF 3 ""))])]
13837   "TARGET_USE_FANCY_MATH_387
13838    && flag_unsafe_math_optimizations"
13839 {
13840   operands[2] = gen_reg_rtx (XFmode);
13841   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
13842 })
13843
13844 (define_expand "atan<mode>2"
13845   [(use (match_operand:MODEF 0 "register_operand" ""))
13846    (use (match_operand:MODEF 1 "register_operand" ""))]
13847   "TARGET_USE_FANCY_MATH_387
13848    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13849        || TARGET_MIX_SSE_I387)
13850    && flag_unsafe_math_optimizations"
13851 {
13852   rtx op0 = gen_reg_rtx (XFmode);
13853
13854   rtx op2 = gen_reg_rtx (<MODE>mode);
13855   emit_move_insn (op2, CONST1_RTX (<MODE>mode));  /* fld1 */
13856
13857   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
13858   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13859   DONE;
13860 })
13861
13862 (define_expand "asinxf2"
13863   [(set (match_dup 2)
13864         (mult:XF (match_operand:XF 1 "register_operand" "")
13865                  (match_dup 1)))
13866    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13867    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13868    (parallel [(set (match_operand:XF 0 "register_operand" "")
13869                    (unspec:XF [(match_dup 5) (match_dup 1)]
13870                               UNSPEC_FPATAN))
13871               (clobber (match_scratch:XF 6 ""))])]
13872   "TARGET_USE_FANCY_MATH_387
13873    && flag_unsafe_math_optimizations"
13874 {
13875   int i;
13876
13877   if (optimize_insn_for_size_p ())
13878     FAIL;
13879
13880   for (i = 2; i < 6; i++)
13881     operands[i] = gen_reg_rtx (XFmode);
13882
13883   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13884 })
13885
13886 (define_expand "asin<mode>2"
13887   [(use (match_operand:MODEF 0 "register_operand" ""))
13888    (use (match_operand:MODEF 1 "general_operand" ""))]
13889  "TARGET_USE_FANCY_MATH_387
13890    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13891        || TARGET_MIX_SSE_I387)
13892    && flag_unsafe_math_optimizations"
13893 {
13894   rtx op0 = gen_reg_rtx (XFmode);
13895   rtx op1 = gen_reg_rtx (XFmode);
13896
13897   if (optimize_insn_for_size_p ())
13898     FAIL;
13899
13900   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13901   emit_insn (gen_asinxf2 (op0, op1));
13902   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13903   DONE;
13904 })
13905
13906 (define_expand "acosxf2"
13907   [(set (match_dup 2)
13908         (mult:XF (match_operand:XF 1 "register_operand" "")
13909                  (match_dup 1)))
13910    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13911    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13912    (parallel [(set (match_operand:XF 0 "register_operand" "")
13913                    (unspec:XF [(match_dup 1) (match_dup 5)]
13914                               UNSPEC_FPATAN))
13915               (clobber (match_scratch:XF 6 ""))])]
13916   "TARGET_USE_FANCY_MATH_387
13917    && flag_unsafe_math_optimizations"
13918 {
13919   int i;
13920
13921   if (optimize_insn_for_size_p ())
13922     FAIL;
13923
13924   for (i = 2; i < 6; i++)
13925     operands[i] = gen_reg_rtx (XFmode);
13926
13927   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13928 })
13929
13930 (define_expand "acos<mode>2"
13931   [(use (match_operand:MODEF 0 "register_operand" ""))
13932    (use (match_operand:MODEF 1 "general_operand" ""))]
13933  "TARGET_USE_FANCY_MATH_387
13934    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13935        || TARGET_MIX_SSE_I387)
13936    && flag_unsafe_math_optimizations"
13937 {
13938   rtx op0 = gen_reg_rtx (XFmode);
13939   rtx op1 = gen_reg_rtx (XFmode);
13940
13941   if (optimize_insn_for_size_p ())
13942     FAIL;
13943
13944   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13945   emit_insn (gen_acosxf2 (op0, op1));
13946   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13947   DONE;
13948 })
13949
13950 (define_insn "fyl2xxf3_i387"
13951   [(set (match_operand:XF 0 "register_operand" "=f")
13952         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13953                     (match_operand:XF 2 "register_operand" "u")]
13954                    UNSPEC_FYL2X))
13955    (clobber (match_scratch:XF 3 "=2"))]
13956   "TARGET_USE_FANCY_MATH_387
13957    && flag_unsafe_math_optimizations"
13958   "fyl2x"
13959   [(set_attr "type" "fpspc")
13960    (set_attr "mode" "XF")])
13961
13962 (define_insn "fyl2x_extend<mode>xf3_i387"
13963   [(set (match_operand:XF 0 "register_operand" "=f")
13964         (unspec:XF [(float_extend:XF
13965                       (match_operand:MODEF 1 "register_operand" "0"))
13966                     (match_operand:XF 2 "register_operand" "u")]
13967                    UNSPEC_FYL2X))
13968    (clobber (match_scratch:XF 3 "=2"))]
13969   "TARGET_USE_FANCY_MATH_387
13970    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13971        || TARGET_MIX_SSE_I387)
13972    && flag_unsafe_math_optimizations"
13973   "fyl2x"
13974   [(set_attr "type" "fpspc")
13975    (set_attr "mode" "XF")])
13976
13977 (define_expand "logxf2"
13978   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13979                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
13980                                (match_dup 2)] UNSPEC_FYL2X))
13981               (clobber (match_scratch:XF 3 ""))])]
13982   "TARGET_USE_FANCY_MATH_387
13983    && flag_unsafe_math_optimizations"
13984 {
13985   operands[2] = gen_reg_rtx (XFmode);
13986   emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
13987 })
13988
13989 (define_expand "log<mode>2"
13990   [(use (match_operand:MODEF 0 "register_operand" ""))
13991    (use (match_operand:MODEF 1 "register_operand" ""))]
13992   "TARGET_USE_FANCY_MATH_387
13993    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13994        || TARGET_MIX_SSE_I387)
13995    && flag_unsafe_math_optimizations"
13996 {
13997   rtx op0 = gen_reg_rtx (XFmode);
13998
13999   rtx op2 = gen_reg_rtx (XFmode);
14000   emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
14001
14002   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14003   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14004   DONE;
14005 })
14006
14007 (define_expand "log10xf2"
14008   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14009                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14010                                (match_dup 2)] UNSPEC_FYL2X))
14011               (clobber (match_scratch:XF 3 ""))])]
14012   "TARGET_USE_FANCY_MATH_387
14013    && flag_unsafe_math_optimizations"
14014 {
14015   operands[2] = gen_reg_rtx (XFmode);
14016   emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
14017 })
14018
14019 (define_expand "log10<mode>2"
14020   [(use (match_operand:MODEF 0 "register_operand" ""))
14021    (use (match_operand:MODEF 1 "register_operand" ""))]
14022   "TARGET_USE_FANCY_MATH_387
14023    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14024        || TARGET_MIX_SSE_I387)
14025    && flag_unsafe_math_optimizations"
14026 {
14027   rtx op0 = gen_reg_rtx (XFmode);
14028
14029   rtx op2 = gen_reg_rtx (XFmode);
14030   emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
14031
14032   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14033   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14034   DONE;
14035 })
14036
14037 (define_expand "log2xf2"
14038   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14039                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14040                                (match_dup 2)] UNSPEC_FYL2X))
14041               (clobber (match_scratch:XF 3 ""))])]
14042   "TARGET_USE_FANCY_MATH_387
14043    && flag_unsafe_math_optimizations"
14044 {
14045   operands[2] = gen_reg_rtx (XFmode);
14046   emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
14047 })
14048
14049 (define_expand "log2<mode>2"
14050   [(use (match_operand:MODEF 0 "register_operand" ""))
14051    (use (match_operand:MODEF 1 "register_operand" ""))]
14052   "TARGET_USE_FANCY_MATH_387
14053    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14054        || TARGET_MIX_SSE_I387)
14055    && flag_unsafe_math_optimizations"
14056 {
14057   rtx op0 = gen_reg_rtx (XFmode);
14058
14059   rtx op2 = gen_reg_rtx (XFmode);
14060   emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
14061
14062   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14063   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14064   DONE;
14065 })
14066
14067 (define_insn "fyl2xp1xf3_i387"
14068   [(set (match_operand:XF 0 "register_operand" "=f")
14069         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
14070                     (match_operand:XF 2 "register_operand" "u")]
14071                    UNSPEC_FYL2XP1))
14072    (clobber (match_scratch:XF 3 "=2"))]
14073   "TARGET_USE_FANCY_MATH_387
14074    && flag_unsafe_math_optimizations"
14075   "fyl2xp1"
14076   [(set_attr "type" "fpspc")
14077    (set_attr "mode" "XF")])
14078
14079 (define_insn "fyl2xp1_extend<mode>xf3_i387"
14080   [(set (match_operand:XF 0 "register_operand" "=f")
14081         (unspec:XF [(float_extend:XF
14082                       (match_operand:MODEF 1 "register_operand" "0"))
14083                     (match_operand:XF 2 "register_operand" "u")]
14084                    UNSPEC_FYL2XP1))
14085    (clobber (match_scratch:XF 3 "=2"))]
14086   "TARGET_USE_FANCY_MATH_387
14087    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14088        || TARGET_MIX_SSE_I387)
14089    && flag_unsafe_math_optimizations"
14090   "fyl2xp1"
14091   [(set_attr "type" "fpspc")
14092    (set_attr "mode" "XF")])
14093
14094 (define_expand "log1pxf2"
14095   [(use (match_operand:XF 0 "register_operand" ""))
14096    (use (match_operand:XF 1 "register_operand" ""))]
14097   "TARGET_USE_FANCY_MATH_387
14098    && flag_unsafe_math_optimizations"
14099 {
14100   if (optimize_insn_for_size_p ())
14101     FAIL;
14102
14103   ix86_emit_i387_log1p (operands[0], operands[1]);
14104   DONE;
14105 })
14106
14107 (define_expand "log1p<mode>2"
14108   [(use (match_operand:MODEF 0 "register_operand" ""))
14109    (use (match_operand:MODEF 1 "register_operand" ""))]
14110   "TARGET_USE_FANCY_MATH_387
14111    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14112        || TARGET_MIX_SSE_I387)
14113    && flag_unsafe_math_optimizations"
14114 {
14115   rtx op0;
14116
14117   if (optimize_insn_for_size_p ())
14118     FAIL;
14119
14120   op0 = gen_reg_rtx (XFmode);
14121
14122   operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
14123
14124   ix86_emit_i387_log1p (op0, operands[1]);
14125   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14126   DONE;
14127 })
14128
14129 (define_insn "fxtractxf3_i387"
14130   [(set (match_operand:XF 0 "register_operand" "=f")
14131         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
14132                    UNSPEC_XTRACT_FRACT))
14133    (set (match_operand:XF 1 "register_operand" "=u")
14134         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
14135   "TARGET_USE_FANCY_MATH_387
14136    && flag_unsafe_math_optimizations"
14137   "fxtract"
14138   [(set_attr "type" "fpspc")
14139    (set_attr "mode" "XF")])
14140
14141 (define_insn "fxtract_extend<mode>xf3_i387"
14142   [(set (match_operand:XF 0 "register_operand" "=f")
14143         (unspec:XF [(float_extend:XF
14144                       (match_operand:MODEF 2 "register_operand" "0"))]
14145                    UNSPEC_XTRACT_FRACT))
14146    (set (match_operand:XF 1 "register_operand" "=u")
14147         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
14148   "TARGET_USE_FANCY_MATH_387
14149    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14150        || TARGET_MIX_SSE_I387)
14151    && flag_unsafe_math_optimizations"
14152   "fxtract"
14153   [(set_attr "type" "fpspc")
14154    (set_attr "mode" "XF")])
14155
14156 (define_expand "logbxf2"
14157   [(parallel [(set (match_dup 2)
14158                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14159                               UNSPEC_XTRACT_FRACT))
14160               (set (match_operand:XF 0 "register_operand" "")
14161                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14162   "TARGET_USE_FANCY_MATH_387
14163    && flag_unsafe_math_optimizations"
14164   "operands[2] = gen_reg_rtx (XFmode);")
14165
14166 (define_expand "logb<mode>2"
14167   [(use (match_operand:MODEF 0 "register_operand" ""))
14168    (use (match_operand:MODEF 1 "register_operand" ""))]
14169   "TARGET_USE_FANCY_MATH_387
14170    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14171        || TARGET_MIX_SSE_I387)
14172    && flag_unsafe_math_optimizations"
14173 {
14174   rtx op0 = gen_reg_rtx (XFmode);
14175   rtx op1 = gen_reg_rtx (XFmode);
14176
14177   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14178   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
14179   DONE;
14180 })
14181
14182 (define_expand "ilogbxf2"
14183   [(use (match_operand:SI 0 "register_operand" ""))
14184    (use (match_operand:XF 1 "register_operand" ""))]
14185   "TARGET_USE_FANCY_MATH_387
14186    && flag_unsafe_math_optimizations"
14187 {
14188   rtx op0, op1;
14189
14190   if (optimize_insn_for_size_p ())
14191     FAIL;
14192
14193   op0 = gen_reg_rtx (XFmode);
14194   op1 = gen_reg_rtx (XFmode);
14195
14196   emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
14197   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14198   DONE;
14199 })
14200
14201 (define_expand "ilogb<mode>2"
14202   [(use (match_operand:SI 0 "register_operand" ""))
14203    (use (match_operand:MODEF 1 "register_operand" ""))]
14204   "TARGET_USE_FANCY_MATH_387
14205    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14206        || TARGET_MIX_SSE_I387)
14207    && flag_unsafe_math_optimizations"
14208 {
14209   rtx op0, op1;
14210
14211   if (optimize_insn_for_size_p ())
14212     FAIL;
14213
14214   op0 = gen_reg_rtx (XFmode);
14215   op1 = gen_reg_rtx (XFmode);
14216
14217   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14218   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14219   DONE;
14220 })
14221
14222 (define_insn "*f2xm1xf2_i387"
14223   [(set (match_operand:XF 0 "register_operand" "=f")
14224         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14225                    UNSPEC_F2XM1))]
14226   "TARGET_USE_FANCY_MATH_387
14227    && flag_unsafe_math_optimizations"
14228   "f2xm1"
14229   [(set_attr "type" "fpspc")
14230    (set_attr "mode" "XF")])
14231
14232 (define_insn "*fscalexf4_i387"
14233   [(set (match_operand:XF 0 "register_operand" "=f")
14234         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14235                     (match_operand:XF 3 "register_operand" "1")]
14236                    UNSPEC_FSCALE_FRACT))
14237    (set (match_operand:XF 1 "register_operand" "=u")
14238         (unspec:XF [(match_dup 2) (match_dup 3)]
14239                    UNSPEC_FSCALE_EXP))]
14240   "TARGET_USE_FANCY_MATH_387
14241    && flag_unsafe_math_optimizations"
14242   "fscale"
14243   [(set_attr "type" "fpspc")
14244    (set_attr "mode" "XF")])
14245
14246 (define_expand "expNcorexf3"
14247   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14248                                (match_operand:XF 2 "register_operand" "")))
14249    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14250    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14251    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14252    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
14253    (parallel [(set (match_operand:XF 0 "register_operand" "")
14254                    (unspec:XF [(match_dup 8) (match_dup 4)]
14255                               UNSPEC_FSCALE_FRACT))
14256               (set (match_dup 9)
14257                    (unspec:XF [(match_dup 8) (match_dup 4)]
14258                               UNSPEC_FSCALE_EXP))])]
14259   "TARGET_USE_FANCY_MATH_387
14260    && flag_unsafe_math_optimizations"
14261 {
14262   int i;
14263
14264   if (optimize_insn_for_size_p ())
14265     FAIL;
14266
14267   for (i = 3; i < 10; i++)
14268     operands[i] = gen_reg_rtx (XFmode);
14269
14270   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
14271 })
14272
14273 (define_expand "expxf2"
14274   [(use (match_operand:XF 0 "register_operand" ""))
14275    (use (match_operand:XF 1 "register_operand" ""))]
14276   "TARGET_USE_FANCY_MATH_387
14277    && flag_unsafe_math_optimizations"
14278 {
14279   rtx op2;
14280
14281   if (optimize_insn_for_size_p ())
14282     FAIL;
14283
14284   op2 = gen_reg_rtx (XFmode);
14285   emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
14286
14287   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14288   DONE;
14289 })
14290
14291 (define_expand "exp<mode>2"
14292   [(use (match_operand:MODEF 0 "register_operand" ""))
14293    (use (match_operand:MODEF 1 "general_operand" ""))]
14294  "TARGET_USE_FANCY_MATH_387
14295    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14296        || TARGET_MIX_SSE_I387)
14297    && flag_unsafe_math_optimizations"
14298 {
14299   rtx op0, op1;
14300
14301   if (optimize_insn_for_size_p ())
14302     FAIL;
14303
14304   op0 = gen_reg_rtx (XFmode);
14305   op1 = gen_reg_rtx (XFmode);
14306
14307   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14308   emit_insn (gen_expxf2 (op0, op1));
14309   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14310   DONE;
14311 })
14312
14313 (define_expand "exp10xf2"
14314   [(use (match_operand:XF 0 "register_operand" ""))
14315    (use (match_operand:XF 1 "register_operand" ""))]
14316   "TARGET_USE_FANCY_MATH_387
14317    && flag_unsafe_math_optimizations"
14318 {
14319   rtx op2;
14320
14321   if (optimize_insn_for_size_p ())
14322     FAIL;
14323
14324   op2 = gen_reg_rtx (XFmode);
14325   emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
14326
14327   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14328   DONE;
14329 })
14330
14331 (define_expand "exp10<mode>2"
14332   [(use (match_operand:MODEF 0 "register_operand" ""))
14333    (use (match_operand:MODEF 1 "general_operand" ""))]
14334  "TARGET_USE_FANCY_MATH_387
14335    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14336        || TARGET_MIX_SSE_I387)
14337    && flag_unsafe_math_optimizations"
14338 {
14339   rtx op0, op1;
14340
14341   if (optimize_insn_for_size_p ())
14342     FAIL;
14343
14344   op0 = gen_reg_rtx (XFmode);
14345   op1 = gen_reg_rtx (XFmode);
14346
14347   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14348   emit_insn (gen_exp10xf2 (op0, op1));
14349   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14350   DONE;
14351 })
14352
14353 (define_expand "exp2xf2"
14354   [(use (match_operand:XF 0 "register_operand" ""))
14355    (use (match_operand:XF 1 "register_operand" ""))]
14356   "TARGET_USE_FANCY_MATH_387
14357    && flag_unsafe_math_optimizations"
14358 {
14359   rtx op2;
14360
14361   if (optimize_insn_for_size_p ())
14362     FAIL;
14363
14364   op2 = gen_reg_rtx (XFmode);
14365   emit_move_insn (op2, CONST1_RTX (XFmode));  /* fld1 */
14366
14367   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14368   DONE;
14369 })
14370
14371 (define_expand "exp2<mode>2"
14372   [(use (match_operand:MODEF 0 "register_operand" ""))
14373    (use (match_operand:MODEF 1 "general_operand" ""))]
14374  "TARGET_USE_FANCY_MATH_387
14375    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14376        || TARGET_MIX_SSE_I387)
14377    && flag_unsafe_math_optimizations"
14378 {
14379   rtx op0, op1;
14380
14381   if (optimize_insn_for_size_p ())
14382     FAIL;
14383
14384   op0 = gen_reg_rtx (XFmode);
14385   op1 = gen_reg_rtx (XFmode);
14386
14387   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14388   emit_insn (gen_exp2xf2 (op0, op1));
14389   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14390   DONE;
14391 })
14392
14393 (define_expand "expm1xf2"
14394   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14395                                (match_dup 2)))
14396    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14397    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14398    (set (match_dup 9) (float_extend:XF (match_dup 13)))
14399    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14400    (parallel [(set (match_dup 7)
14401                    (unspec:XF [(match_dup 6) (match_dup 4)]
14402                               UNSPEC_FSCALE_FRACT))
14403               (set (match_dup 8)
14404                    (unspec:XF [(match_dup 6) (match_dup 4)]
14405                               UNSPEC_FSCALE_EXP))])
14406    (parallel [(set (match_dup 10)
14407                    (unspec:XF [(match_dup 9) (match_dup 8)]
14408                               UNSPEC_FSCALE_FRACT))
14409               (set (match_dup 11)
14410                    (unspec:XF [(match_dup 9) (match_dup 8)]
14411                               UNSPEC_FSCALE_EXP))])
14412    (set (match_dup 12) (minus:XF (match_dup 10)
14413                                  (float_extend:XF (match_dup 13))))
14414    (set (match_operand:XF 0 "register_operand" "")
14415         (plus:XF (match_dup 12) (match_dup 7)))]
14416   "TARGET_USE_FANCY_MATH_387
14417    && flag_unsafe_math_optimizations"
14418 {
14419   int i;
14420
14421   if (optimize_insn_for_size_p ())
14422     FAIL;
14423
14424   for (i = 2; i < 13; i++)
14425     operands[i] = gen_reg_rtx (XFmode);
14426
14427   operands[13]
14428     = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
14429
14430   emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
14431 })
14432
14433 (define_expand "expm1<mode>2"
14434   [(use (match_operand:MODEF 0 "register_operand" ""))
14435    (use (match_operand:MODEF 1 "general_operand" ""))]
14436  "TARGET_USE_FANCY_MATH_387
14437    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14438        || TARGET_MIX_SSE_I387)
14439    && flag_unsafe_math_optimizations"
14440 {
14441   rtx op0, op1;
14442
14443   if (optimize_insn_for_size_p ())
14444     FAIL;
14445
14446   op0 = gen_reg_rtx (XFmode);
14447   op1 = gen_reg_rtx (XFmode);
14448
14449   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14450   emit_insn (gen_expm1xf2 (op0, op1));
14451   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14452   DONE;
14453 })
14454
14455 (define_expand "ldexpxf3"
14456   [(set (match_dup 3)
14457         (float:XF (match_operand:SI 2 "register_operand" "")))
14458    (parallel [(set (match_operand:XF 0 " register_operand" "")
14459                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14460                                (match_dup 3)]
14461                               UNSPEC_FSCALE_FRACT))
14462               (set (match_dup 4)
14463                    (unspec:XF [(match_dup 1) (match_dup 3)]
14464                               UNSPEC_FSCALE_EXP))])]
14465   "TARGET_USE_FANCY_MATH_387
14466    && flag_unsafe_math_optimizations"
14467 {
14468   if (optimize_insn_for_size_p ())
14469     FAIL;
14470
14471   operands[3] = gen_reg_rtx (XFmode);
14472   operands[4] = gen_reg_rtx (XFmode);
14473 })
14474
14475 (define_expand "ldexp<mode>3"
14476   [(use (match_operand:MODEF 0 "register_operand" ""))
14477    (use (match_operand:MODEF 1 "general_operand" ""))
14478    (use (match_operand:SI 2 "register_operand" ""))]
14479  "TARGET_USE_FANCY_MATH_387
14480    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14481        || TARGET_MIX_SSE_I387)
14482    && flag_unsafe_math_optimizations"
14483 {
14484   rtx op0, op1;
14485
14486   if (optimize_insn_for_size_p ())
14487     FAIL;
14488
14489   op0 = gen_reg_rtx (XFmode);
14490   op1 = gen_reg_rtx (XFmode);
14491
14492   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14493   emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
14494   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14495   DONE;
14496 })
14497
14498 (define_expand "scalbxf3"
14499   [(parallel [(set (match_operand:XF 0 " register_operand" "")
14500                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14501                                (match_operand:XF 2 "register_operand" "")]
14502                               UNSPEC_FSCALE_FRACT))
14503               (set (match_dup 3)
14504                    (unspec:XF [(match_dup 1) (match_dup 2)]
14505                               UNSPEC_FSCALE_EXP))])]
14506   "TARGET_USE_FANCY_MATH_387
14507    && flag_unsafe_math_optimizations"
14508 {
14509   if (optimize_insn_for_size_p ())
14510     FAIL;
14511
14512   operands[3] = gen_reg_rtx (XFmode);
14513 })
14514
14515 (define_expand "scalb<mode>3"
14516   [(use (match_operand:MODEF 0 "register_operand" ""))
14517    (use (match_operand:MODEF 1 "general_operand" ""))
14518    (use (match_operand:MODEF 2 "general_operand" ""))]
14519  "TARGET_USE_FANCY_MATH_387
14520    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14521        || TARGET_MIX_SSE_I387)
14522    && flag_unsafe_math_optimizations"
14523 {
14524   rtx op0, op1, op2;
14525
14526   if (optimize_insn_for_size_p ())
14527     FAIL;
14528
14529   op0 = gen_reg_rtx (XFmode);
14530   op1 = gen_reg_rtx (XFmode);
14531   op2 = gen_reg_rtx (XFmode);
14532
14533   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14534   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
14535   emit_insn (gen_scalbxf3 (op0, op1, op2));
14536   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14537   DONE;
14538 })
14539
14540 (define_expand "significandxf2"
14541   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14542                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14543                               UNSPEC_XTRACT_FRACT))
14544               (set (match_dup 2)
14545                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14546   "TARGET_USE_FANCY_MATH_387
14547    && flag_unsafe_math_optimizations"
14548   "operands[2] = gen_reg_rtx (XFmode);")
14549
14550 (define_expand "significand<mode>2"
14551   [(use (match_operand:MODEF 0 "register_operand" ""))
14552    (use (match_operand:MODEF 1 "register_operand" ""))]
14553   "TARGET_USE_FANCY_MATH_387
14554    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14555        || TARGET_MIX_SSE_I387)
14556    && flag_unsafe_math_optimizations"
14557 {
14558   rtx op0 = gen_reg_rtx (XFmode);
14559   rtx op1 = gen_reg_rtx (XFmode);
14560
14561   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14562   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14563   DONE;
14564 })
14565 \f
14566
14567 (define_insn "sse4_1_round<mode>2"
14568   [(set (match_operand:MODEF 0 "register_operand" "=x")
14569         (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
14570                        (match_operand:SI 2 "const_0_to_15_operand" "n")]
14571                       UNSPEC_ROUND))]
14572   "TARGET_ROUND"
14573   "%vround<ssemodesuffix>\t{%2, %1, %d0|%d0, %1, %2}"
14574   [(set_attr "type" "ssecvt")
14575    (set_attr "prefix_extra" "1")
14576    (set_attr "prefix" "maybe_vex")
14577    (set_attr "mode" "<MODE>")])
14578
14579 (define_insn "rintxf2"
14580   [(set (match_operand:XF 0 "register_operand" "=f")
14581         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14582                    UNSPEC_FRNDINT))]
14583   "TARGET_USE_FANCY_MATH_387
14584    && flag_unsafe_math_optimizations"
14585   "frndint"
14586   [(set_attr "type" "fpspc")
14587    (set_attr "mode" "XF")])
14588
14589 (define_expand "rint<mode>2"
14590   [(use (match_operand:MODEF 0 "register_operand" ""))
14591    (use (match_operand:MODEF 1 "register_operand" ""))]
14592   "(TARGET_USE_FANCY_MATH_387
14593     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14594         || TARGET_MIX_SSE_I387)
14595     && flag_unsafe_math_optimizations)
14596    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14597        && !flag_trapping_math)"
14598 {
14599   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14600       && !flag_trapping_math)
14601     {
14602       if (TARGET_ROUND)
14603         emit_insn (gen_sse4_1_round<mode>2
14604                    (operands[0], operands[1], GEN_INT (ROUND_MXCSR)));
14605       else if (optimize_insn_for_size_p ())
14606         FAIL;
14607       else
14608         ix86_expand_rint (operands[0], operands[1]);
14609     }
14610   else
14611     {
14612       rtx op0 = gen_reg_rtx (XFmode);
14613       rtx op1 = gen_reg_rtx (XFmode);
14614
14615       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14616       emit_insn (gen_rintxf2 (op0, op1));
14617
14618       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14619     }
14620   DONE;
14621 })
14622
14623 (define_expand "round<mode>2"
14624   [(match_operand:X87MODEF 0 "register_operand" "")
14625    (match_operand:X87MODEF 1 "nonimmediate_operand" "")]
14626   "(TARGET_USE_FANCY_MATH_387
14627     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14628         || TARGET_MIX_SSE_I387)
14629     && flag_unsafe_math_optimizations)
14630    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14631        && !flag_trapping_math && !flag_rounding_math)"
14632 {
14633   if (optimize_insn_for_size_p ())
14634     FAIL;
14635
14636   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14637       && !flag_trapping_math && !flag_rounding_math)
14638     {
14639       if (TARGET_ROUND)
14640         {
14641           operands[1] = force_reg (<MODE>mode, operands[1]);
14642           ix86_expand_round_sse4 (operands[0], operands[1]);
14643         }
14644       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14645         ix86_expand_round (operands[0], operands[1]);
14646       else
14647         ix86_expand_rounddf_32 (operands[0], operands[1]);
14648     }
14649   else
14650     {
14651       operands[1] = force_reg (<MODE>mode, operands[1]);
14652       ix86_emit_i387_round (operands[0], operands[1]);
14653     }
14654   DONE;
14655 })
14656
14657 (define_insn_and_split "*fistdi2_1"
14658   [(set (match_operand:DI 0 "nonimmediate_operand" "")
14659         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14660                    UNSPEC_FIST))]
14661   "TARGET_USE_FANCY_MATH_387
14662    && can_create_pseudo_p ()"
14663   "#"
14664   "&& 1"
14665   [(const_int 0)]
14666 {
14667   if (memory_operand (operands[0], VOIDmode))
14668     emit_insn (gen_fistdi2 (operands[0], operands[1]));
14669   else
14670     {
14671       operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
14672       emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
14673                                          operands[2]));
14674     }
14675   DONE;
14676 }
14677   [(set_attr "type" "fpspc")
14678    (set_attr "mode" "DI")])
14679
14680 (define_insn "fistdi2"
14681   [(set (match_operand:DI 0 "memory_operand" "=m")
14682         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14683                    UNSPEC_FIST))
14684    (clobber (match_scratch:XF 2 "=&1f"))]
14685   "TARGET_USE_FANCY_MATH_387"
14686   "* return output_fix_trunc (insn, operands, false);"
14687   [(set_attr "type" "fpspc")
14688    (set_attr "mode" "DI")])
14689
14690 (define_insn "fistdi2_with_temp"
14691   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14692         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14693                    UNSPEC_FIST))
14694    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))
14695    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
14696   "TARGET_USE_FANCY_MATH_387"
14697   "#"
14698   [(set_attr "type" "fpspc")
14699    (set_attr "mode" "DI")])
14700
14701 (define_split
14702   [(set (match_operand:DI 0 "register_operand" "")
14703         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14704                    UNSPEC_FIST))
14705    (clobber (match_operand:DI 2 "memory_operand" ""))
14706    (clobber (match_scratch 3 ""))]
14707   "reload_completed"
14708   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14709               (clobber (match_dup 3))])
14710    (set (match_dup 0) (match_dup 2))])
14711
14712 (define_split
14713   [(set (match_operand:DI 0 "memory_operand" "")
14714         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14715                    UNSPEC_FIST))
14716    (clobber (match_operand:DI 2 "memory_operand" ""))
14717    (clobber (match_scratch 3 ""))]
14718   "reload_completed"
14719   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14720               (clobber (match_dup 3))])])
14721
14722 (define_insn_and_split "*fist<mode>2_1"
14723   [(set (match_operand:SWI24 0 "register_operand" "")
14724         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14725                       UNSPEC_FIST))]
14726   "TARGET_USE_FANCY_MATH_387
14727    && can_create_pseudo_p ()"
14728   "#"
14729   "&& 1"
14730   [(const_int 0)]
14731 {
14732   operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14733   emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
14734                                         operands[2]));
14735   DONE;
14736 }
14737   [(set_attr "type" "fpspc")
14738    (set_attr "mode" "<MODE>")])
14739
14740 (define_insn "fist<mode>2"
14741   [(set (match_operand:SWI24 0 "memory_operand" "=m")
14742         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14743                       UNSPEC_FIST))]
14744   "TARGET_USE_FANCY_MATH_387"
14745   "* return output_fix_trunc (insn, operands, false);"
14746   [(set_attr "type" "fpspc")
14747    (set_attr "mode" "<MODE>")])
14748
14749 (define_insn "fist<mode>2_with_temp"
14750   [(set (match_operand:SWI24 0 "register_operand" "=r")
14751         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14752                       UNSPEC_FIST))
14753    (clobber (match_operand:SWI24 2 "memory_operand" "=m"))]
14754   "TARGET_USE_FANCY_MATH_387"
14755   "#"
14756   [(set_attr "type" "fpspc")
14757    (set_attr "mode" "<MODE>")])
14758
14759 (define_split
14760   [(set (match_operand:SWI24 0 "register_operand" "")
14761         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14762                       UNSPEC_FIST))
14763    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14764   "reload_completed"
14765   [(set (match_dup 2) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))
14766    (set (match_dup 0) (match_dup 2))])
14767
14768 (define_split
14769   [(set (match_operand:SWI24 0 "memory_operand" "")
14770         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14771                       UNSPEC_FIST))
14772    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14773   "reload_completed"
14774   [(set (match_dup 0) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))])
14775
14776 (define_expand "lrintxf<mode>2"
14777   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14778      (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14779                      UNSPEC_FIST))]
14780   "TARGET_USE_FANCY_MATH_387")
14781
14782 (define_expand "lrint<MODEF:mode><SWI48x:mode>2"
14783   [(set (match_operand:SWI48x 0 "nonimmediate_operand" "")
14784      (unspec:SWI48x [(match_operand:MODEF 1 "register_operand" "")]
14785                         UNSPEC_FIX_NOTRUNC))]
14786   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
14787    && ((<SWI48x:MODE>mode != DImode) || TARGET_64BIT)")
14788
14789 (define_expand "lround<X87MODEF:mode><SWI248x:mode>2"
14790   [(match_operand:SWI248x 0 "nonimmediate_operand" "")
14791    (match_operand:X87MODEF 1 "register_operand" "")]
14792   "(TARGET_USE_FANCY_MATH_387
14793     && (!(SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
14794         || TARGET_MIX_SSE_I387)
14795     && flag_unsafe_math_optimizations)
14796    || (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14797        && <SWI248x:MODE>mode != HImode 
14798        && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14799        && !flag_trapping_math && !flag_rounding_math)"
14800 {
14801   if (optimize_insn_for_size_p ())
14802     FAIL;
14803
14804   if (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14805       && <SWI248x:MODE>mode != HImode
14806       && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14807       && !flag_trapping_math && !flag_rounding_math)
14808     ix86_expand_lround (operands[0], operands[1]);
14809   else
14810     ix86_emit_i387_round (operands[0], operands[1]);
14811   DONE;
14812 })
14813
14814 ;; Rounding mode control word calculation could clobber FLAGS_REG.
14815 (define_insn_and_split "frndintxf2_floor"
14816   [(set (match_operand:XF 0 "register_operand" "")
14817         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14818          UNSPEC_FRNDINT_FLOOR))
14819    (clobber (reg:CC FLAGS_REG))]
14820   "TARGET_USE_FANCY_MATH_387
14821    && flag_unsafe_math_optimizations
14822    && can_create_pseudo_p ()"
14823   "#"
14824   "&& 1"
14825   [(const_int 0)]
14826 {
14827   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14828
14829   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14830   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14831
14832   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
14833                                         operands[2], operands[3]));
14834   DONE;
14835 }
14836   [(set_attr "type" "frndint")
14837    (set_attr "i387_cw" "floor")
14838    (set_attr "mode" "XF")])
14839
14840 (define_insn "frndintxf2_floor_i387"
14841   [(set (match_operand:XF 0 "register_operand" "=f")
14842         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14843          UNSPEC_FRNDINT_FLOOR))
14844    (use (match_operand:HI 2 "memory_operand" "m"))
14845    (use (match_operand:HI 3 "memory_operand" "m"))]
14846   "TARGET_USE_FANCY_MATH_387
14847    && flag_unsafe_math_optimizations"
14848   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
14849   [(set_attr "type" "frndint")
14850    (set_attr "i387_cw" "floor")
14851    (set_attr "mode" "XF")])
14852
14853 (define_expand "floorxf2"
14854   [(use (match_operand:XF 0 "register_operand" ""))
14855    (use (match_operand:XF 1 "register_operand" ""))]
14856   "TARGET_USE_FANCY_MATH_387
14857    && flag_unsafe_math_optimizations"
14858 {
14859   if (optimize_insn_for_size_p ())
14860     FAIL;
14861   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
14862   DONE;
14863 })
14864
14865 (define_expand "floor<mode>2"
14866   [(use (match_operand:MODEF 0 "register_operand" ""))
14867    (use (match_operand:MODEF 1 "register_operand" ""))]
14868   "(TARGET_USE_FANCY_MATH_387
14869     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14870         || TARGET_MIX_SSE_I387)
14871     && flag_unsafe_math_optimizations)
14872    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14873        && !flag_trapping_math)"
14874 {
14875   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14876       && !flag_trapping_math)
14877     {
14878       if (TARGET_ROUND)
14879         emit_insn (gen_sse4_1_round<mode>2
14880                    (operands[0], operands[1], GEN_INT (ROUND_FLOOR)));
14881       else if (optimize_insn_for_size_p ())
14882         FAIL;
14883       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14884         ix86_expand_floorceil (operands[0], operands[1], true);
14885       else
14886         ix86_expand_floorceildf_32 (operands[0], operands[1], true);
14887     }
14888   else
14889     {
14890       rtx op0, op1;
14891
14892       if (optimize_insn_for_size_p ())
14893         FAIL;
14894
14895       op0 = gen_reg_rtx (XFmode);
14896       op1 = gen_reg_rtx (XFmode);
14897       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14898       emit_insn (gen_frndintxf2_floor (op0, op1));
14899
14900       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14901     }
14902   DONE;
14903 })
14904
14905 (define_insn_and_split "*fist<mode>2_floor_1"
14906   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14907         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14908                         UNSPEC_FIST_FLOOR))
14909    (clobber (reg:CC FLAGS_REG))]
14910   "TARGET_USE_FANCY_MATH_387
14911    && flag_unsafe_math_optimizations
14912    && can_create_pseudo_p ()"
14913   "#"
14914   "&& 1"
14915   [(const_int 0)]
14916 {
14917   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14918
14919   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14920   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14921   if (memory_operand (operands[0], VOIDmode))
14922     emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
14923                                       operands[2], operands[3]));
14924   else
14925     {
14926       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14927       emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
14928                                                   operands[2], operands[3],
14929                                                   operands[4]));
14930     }
14931   DONE;
14932 }
14933   [(set_attr "type" "fistp")
14934    (set_attr "i387_cw" "floor")
14935    (set_attr "mode" "<MODE>")])
14936
14937 (define_insn "fistdi2_floor"
14938   [(set (match_operand:DI 0 "memory_operand" "=m")
14939         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14940                    UNSPEC_FIST_FLOOR))
14941    (use (match_operand:HI 2 "memory_operand" "m"))
14942    (use (match_operand:HI 3 "memory_operand" "m"))
14943    (clobber (match_scratch:XF 4 "=&1f"))]
14944   "TARGET_USE_FANCY_MATH_387
14945    && flag_unsafe_math_optimizations"
14946   "* return output_fix_trunc (insn, operands, false);"
14947   [(set_attr "type" "fistp")
14948    (set_attr "i387_cw" "floor")
14949    (set_attr "mode" "DI")])
14950
14951 (define_insn "fistdi2_floor_with_temp"
14952   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14953         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14954                    UNSPEC_FIST_FLOOR))
14955    (use (match_operand:HI 2 "memory_operand" "m,m"))
14956    (use (match_operand:HI 3 "memory_operand" "m,m"))
14957    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
14958    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
14959   "TARGET_USE_FANCY_MATH_387
14960    && flag_unsafe_math_optimizations"
14961   "#"
14962   [(set_attr "type" "fistp")
14963    (set_attr "i387_cw" "floor")
14964    (set_attr "mode" "DI")])
14965
14966 (define_split
14967   [(set (match_operand:DI 0 "register_operand" "")
14968         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14969                    UNSPEC_FIST_FLOOR))
14970    (use (match_operand:HI 2 "memory_operand" ""))
14971    (use (match_operand:HI 3 "memory_operand" ""))
14972    (clobber (match_operand:DI 4 "memory_operand" ""))
14973    (clobber (match_scratch 5 ""))]
14974   "reload_completed"
14975   [(parallel [(set (match_dup 4)
14976                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
14977               (use (match_dup 2))
14978               (use (match_dup 3))
14979               (clobber (match_dup 5))])
14980    (set (match_dup 0) (match_dup 4))])
14981
14982 (define_split
14983   [(set (match_operand:DI 0 "memory_operand" "")
14984         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14985                    UNSPEC_FIST_FLOOR))
14986    (use (match_operand:HI 2 "memory_operand" ""))
14987    (use (match_operand:HI 3 "memory_operand" ""))
14988    (clobber (match_operand:DI 4 "memory_operand" ""))
14989    (clobber (match_scratch 5 ""))]
14990   "reload_completed"
14991   [(parallel [(set (match_dup 0)
14992                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
14993               (use (match_dup 2))
14994               (use (match_dup 3))
14995               (clobber (match_dup 5))])])
14996
14997 (define_insn "fist<mode>2_floor"
14998   [(set (match_operand:SWI24 0 "memory_operand" "=m")
14999         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
15000                       UNSPEC_FIST_FLOOR))
15001    (use (match_operand:HI 2 "memory_operand" "m"))
15002    (use (match_operand:HI 3 "memory_operand" "m"))]
15003   "TARGET_USE_FANCY_MATH_387
15004    && flag_unsafe_math_optimizations"
15005   "* return output_fix_trunc (insn, operands, false);"
15006   [(set_attr "type" "fistp")
15007    (set_attr "i387_cw" "floor")
15008    (set_attr "mode" "<MODE>")])
15009
15010 (define_insn "fist<mode>2_floor_with_temp"
15011   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15012         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15013                       UNSPEC_FIST_FLOOR))
15014    (use (match_operand:HI 2 "memory_operand" "m,m"))
15015    (use (match_operand:HI 3 "memory_operand" "m,m"))
15016    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15017   "TARGET_USE_FANCY_MATH_387
15018    && flag_unsafe_math_optimizations"
15019   "#"
15020   [(set_attr "type" "fistp")
15021    (set_attr "i387_cw" "floor")
15022    (set_attr "mode" "<MODE>")])
15023
15024 (define_split
15025   [(set (match_operand:SWI24 0 "register_operand" "")
15026         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15027                       UNSPEC_FIST_FLOOR))
15028    (use (match_operand:HI 2 "memory_operand" ""))
15029    (use (match_operand:HI 3 "memory_operand" ""))
15030    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15031   "reload_completed"
15032   [(parallel [(set (match_dup 4)
15033                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15034               (use (match_dup 2))
15035               (use (match_dup 3))])
15036    (set (match_dup 0) (match_dup 4))])
15037
15038 (define_split
15039   [(set (match_operand:SWI24 0 "memory_operand" "")
15040         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15041                       UNSPEC_FIST_FLOOR))
15042    (use (match_operand:HI 2 "memory_operand" ""))
15043    (use (match_operand:HI 3 "memory_operand" ""))
15044    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15045   "reload_completed"
15046   [(parallel [(set (match_dup 0)
15047                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15048               (use (match_dup 2))
15049               (use (match_dup 3))])])
15050
15051 (define_expand "lfloorxf<mode>2"
15052   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15053                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15054                                    UNSPEC_FIST_FLOOR))
15055               (clobber (reg:CC FLAGS_REG))])]
15056   "TARGET_USE_FANCY_MATH_387
15057    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15058    && flag_unsafe_math_optimizations")
15059
15060 (define_expand "lfloor<MODEF:mode><SWI48:mode>2"
15061   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15062    (match_operand:MODEF 1 "register_operand" "")]
15063   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15064    && !flag_trapping_math"
15065 {
15066   if (TARGET_64BIT && optimize_insn_for_size_p ())
15067     FAIL;
15068   ix86_expand_lfloorceil (operands[0], operands[1], true);
15069   DONE;
15070 })
15071
15072 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15073 (define_insn_and_split "frndintxf2_ceil"
15074   [(set (match_operand:XF 0 "register_operand" "")
15075         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15076          UNSPEC_FRNDINT_CEIL))
15077    (clobber (reg:CC FLAGS_REG))]
15078   "TARGET_USE_FANCY_MATH_387
15079    && flag_unsafe_math_optimizations
15080    && can_create_pseudo_p ()"
15081   "#"
15082   "&& 1"
15083   [(const_int 0)]
15084 {
15085   ix86_optimize_mode_switching[I387_CEIL] = 1;
15086
15087   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15088   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15089
15090   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
15091                                        operands[2], operands[3]));
15092   DONE;
15093 }
15094   [(set_attr "type" "frndint")
15095    (set_attr "i387_cw" "ceil")
15096    (set_attr "mode" "XF")])
15097
15098 (define_insn "frndintxf2_ceil_i387"
15099   [(set (match_operand:XF 0 "register_operand" "=f")
15100         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15101          UNSPEC_FRNDINT_CEIL))
15102    (use (match_operand:HI 2 "memory_operand" "m"))
15103    (use (match_operand:HI 3 "memory_operand" "m"))]
15104   "TARGET_USE_FANCY_MATH_387
15105    && flag_unsafe_math_optimizations"
15106   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15107   [(set_attr "type" "frndint")
15108    (set_attr "i387_cw" "ceil")
15109    (set_attr "mode" "XF")])
15110
15111 (define_expand "ceilxf2"
15112   [(use (match_operand:XF 0 "register_operand" ""))
15113    (use (match_operand:XF 1 "register_operand" ""))]
15114   "TARGET_USE_FANCY_MATH_387
15115    && flag_unsafe_math_optimizations"
15116 {
15117   if (optimize_insn_for_size_p ())
15118     FAIL;
15119   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
15120   DONE;
15121 })
15122
15123 (define_expand "ceil<mode>2"
15124   [(use (match_operand:MODEF 0 "register_operand" ""))
15125    (use (match_operand:MODEF 1 "register_operand" ""))]
15126   "(TARGET_USE_FANCY_MATH_387
15127     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15128         || TARGET_MIX_SSE_I387)
15129     && flag_unsafe_math_optimizations)
15130    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15131        && !flag_trapping_math)"
15132 {
15133   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15134       && !flag_trapping_math)
15135     {
15136       if (TARGET_ROUND)
15137         emit_insn (gen_sse4_1_round<mode>2
15138                    (operands[0], operands[1], GEN_INT (ROUND_CEIL)));
15139       else if (optimize_insn_for_size_p ())
15140         FAIL;
15141       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15142         ix86_expand_floorceil (operands[0], operands[1], false);
15143       else
15144         ix86_expand_floorceildf_32 (operands[0], operands[1], false);
15145     }
15146   else
15147     {
15148       rtx op0, op1;
15149
15150       if (optimize_insn_for_size_p ())
15151         FAIL;
15152
15153       op0 = gen_reg_rtx (XFmode);
15154       op1 = gen_reg_rtx (XFmode);
15155       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15156       emit_insn (gen_frndintxf2_ceil (op0, op1));
15157
15158       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15159     }
15160   DONE;
15161 })
15162
15163 (define_insn_and_split "*fist<mode>2_ceil_1"
15164   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15165         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15166                         UNSPEC_FIST_CEIL))
15167    (clobber (reg:CC FLAGS_REG))]
15168   "TARGET_USE_FANCY_MATH_387
15169    && flag_unsafe_math_optimizations
15170    && can_create_pseudo_p ()"
15171   "#"
15172   "&& 1"
15173   [(const_int 0)]
15174 {
15175   ix86_optimize_mode_switching[I387_CEIL] = 1;
15176
15177   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15178   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15179   if (memory_operand (operands[0], VOIDmode))
15180     emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
15181                                      operands[2], operands[3]));
15182   else
15183     {
15184       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
15185       emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
15186                                                  operands[2], operands[3],
15187                                                  operands[4]));
15188     }
15189   DONE;
15190 }
15191   [(set_attr "type" "fistp")
15192    (set_attr "i387_cw" "ceil")
15193    (set_attr "mode" "<MODE>")])
15194
15195 (define_insn "fistdi2_ceil"
15196   [(set (match_operand:DI 0 "memory_operand" "=m")
15197         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
15198                    UNSPEC_FIST_CEIL))
15199    (use (match_operand:HI 2 "memory_operand" "m"))
15200    (use (match_operand:HI 3 "memory_operand" "m"))
15201    (clobber (match_scratch:XF 4 "=&1f"))]
15202   "TARGET_USE_FANCY_MATH_387
15203    && flag_unsafe_math_optimizations"
15204   "* return output_fix_trunc (insn, operands, false);"
15205   [(set_attr "type" "fistp")
15206    (set_attr "i387_cw" "ceil")
15207    (set_attr "mode" "DI")])
15208
15209 (define_insn "fistdi2_ceil_with_temp"
15210   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
15211         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
15212                    UNSPEC_FIST_CEIL))
15213    (use (match_operand:HI 2 "memory_operand" "m,m"))
15214    (use (match_operand:HI 3 "memory_operand" "m,m"))
15215    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
15216    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
15217   "TARGET_USE_FANCY_MATH_387
15218    && flag_unsafe_math_optimizations"
15219   "#"
15220   [(set_attr "type" "fistp")
15221    (set_attr "i387_cw" "ceil")
15222    (set_attr "mode" "DI")])
15223
15224 (define_split
15225   [(set (match_operand:DI 0 "register_operand" "")
15226         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15227                    UNSPEC_FIST_CEIL))
15228    (use (match_operand:HI 2 "memory_operand" ""))
15229    (use (match_operand:HI 3 "memory_operand" ""))
15230    (clobber (match_operand:DI 4 "memory_operand" ""))
15231    (clobber (match_scratch 5 ""))]
15232   "reload_completed"
15233   [(parallel [(set (match_dup 4)
15234                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15235               (use (match_dup 2))
15236               (use (match_dup 3))
15237               (clobber (match_dup 5))])
15238    (set (match_dup 0) (match_dup 4))])
15239
15240 (define_split
15241   [(set (match_operand:DI 0 "memory_operand" "")
15242         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15243                    UNSPEC_FIST_CEIL))
15244    (use (match_operand:HI 2 "memory_operand" ""))
15245    (use (match_operand:HI 3 "memory_operand" ""))
15246    (clobber (match_operand:DI 4 "memory_operand" ""))
15247    (clobber (match_scratch 5 ""))]
15248   "reload_completed"
15249   [(parallel [(set (match_dup 0)
15250                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15251               (use (match_dup 2))
15252               (use (match_dup 3))
15253               (clobber (match_dup 5))])])
15254
15255 (define_insn "fist<mode>2_ceil"
15256   [(set (match_operand:SWI24 0 "memory_operand" "=m")
15257         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
15258                       UNSPEC_FIST_CEIL))
15259    (use (match_operand:HI 2 "memory_operand" "m"))
15260    (use (match_operand:HI 3 "memory_operand" "m"))]
15261   "TARGET_USE_FANCY_MATH_387
15262    && flag_unsafe_math_optimizations"
15263   "* return output_fix_trunc (insn, operands, false);"
15264   [(set_attr "type" "fistp")
15265    (set_attr "i387_cw" "ceil")
15266    (set_attr "mode" "<MODE>")])
15267
15268 (define_insn "fist<mode>2_ceil_with_temp"
15269   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15270         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15271                       UNSPEC_FIST_CEIL))
15272    (use (match_operand:HI 2 "memory_operand" "m,m"))
15273    (use (match_operand:HI 3 "memory_operand" "m,m"))
15274    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15275   "TARGET_USE_FANCY_MATH_387
15276    && flag_unsafe_math_optimizations"
15277   "#"
15278   [(set_attr "type" "fistp")
15279    (set_attr "i387_cw" "ceil")
15280    (set_attr "mode" "<MODE>")])
15281
15282 (define_split
15283   [(set (match_operand:SWI24 0 "register_operand" "")
15284         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15285                       UNSPEC_FIST_CEIL))
15286    (use (match_operand:HI 2 "memory_operand" ""))
15287    (use (match_operand:HI 3 "memory_operand" ""))
15288    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15289   "reload_completed"
15290   [(parallel [(set (match_dup 4)
15291                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15292               (use (match_dup 2))
15293               (use (match_dup 3))])
15294    (set (match_dup 0) (match_dup 4))])
15295
15296 (define_split
15297   [(set (match_operand:SWI24 0 "memory_operand" "")
15298         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15299                       UNSPEC_FIST_CEIL))
15300    (use (match_operand:HI 2 "memory_operand" ""))
15301    (use (match_operand:HI 3 "memory_operand" ""))
15302    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15303   "reload_completed"
15304   [(parallel [(set (match_dup 0)
15305                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15306               (use (match_dup 2))
15307               (use (match_dup 3))])])
15308
15309 (define_expand "lceilxf<mode>2"
15310   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15311                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15312                                    UNSPEC_FIST_CEIL))
15313               (clobber (reg:CC FLAGS_REG))])]
15314   "TARGET_USE_FANCY_MATH_387
15315    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15316    && flag_unsafe_math_optimizations")
15317
15318 (define_expand "lceil<MODEF:mode><SWI48:mode>2"
15319   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15320    (match_operand:MODEF 1 "register_operand" "")]
15321   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15322    && !flag_trapping_math"
15323 {
15324   ix86_expand_lfloorceil (operands[0], operands[1], false);
15325   DONE;
15326 })
15327
15328 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15329 (define_insn_and_split "frndintxf2_trunc"
15330   [(set (match_operand:XF 0 "register_operand" "")
15331         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15332          UNSPEC_FRNDINT_TRUNC))
15333    (clobber (reg:CC FLAGS_REG))]
15334   "TARGET_USE_FANCY_MATH_387
15335    && flag_unsafe_math_optimizations
15336    && can_create_pseudo_p ()"
15337   "#"
15338   "&& 1"
15339   [(const_int 0)]
15340 {
15341   ix86_optimize_mode_switching[I387_TRUNC] = 1;
15342
15343   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15344   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
15345
15346   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
15347                                         operands[2], operands[3]));
15348   DONE;
15349 }
15350   [(set_attr "type" "frndint")
15351    (set_attr "i387_cw" "trunc")
15352    (set_attr "mode" "XF")])
15353
15354 (define_insn "frndintxf2_trunc_i387"
15355   [(set (match_operand:XF 0 "register_operand" "=f")
15356         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15357          UNSPEC_FRNDINT_TRUNC))
15358    (use (match_operand:HI 2 "memory_operand" "m"))
15359    (use (match_operand:HI 3 "memory_operand" "m"))]
15360   "TARGET_USE_FANCY_MATH_387
15361    && flag_unsafe_math_optimizations"
15362   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15363   [(set_attr "type" "frndint")
15364    (set_attr "i387_cw" "trunc")
15365    (set_attr "mode" "XF")])
15366
15367 (define_expand "btruncxf2"
15368   [(use (match_operand:XF 0 "register_operand" ""))
15369    (use (match_operand:XF 1 "register_operand" ""))]
15370   "TARGET_USE_FANCY_MATH_387
15371    && flag_unsafe_math_optimizations"
15372 {
15373   if (optimize_insn_for_size_p ())
15374     FAIL;
15375   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
15376   DONE;
15377 })
15378
15379 (define_expand "btrunc<mode>2"
15380   [(use (match_operand:MODEF 0 "register_operand" ""))
15381    (use (match_operand:MODEF 1 "register_operand" ""))]
15382   "(TARGET_USE_FANCY_MATH_387
15383     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15384         || TARGET_MIX_SSE_I387)
15385     && flag_unsafe_math_optimizations)
15386    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15387        && !flag_trapping_math)"
15388 {
15389   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15390       && !flag_trapping_math)
15391     {
15392       if (TARGET_ROUND)
15393         emit_insn (gen_sse4_1_round<mode>2
15394                    (operands[0], operands[1], GEN_INT (ROUND_TRUNC)));
15395       else if (optimize_insn_for_size_p ())
15396         FAIL;
15397       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15398         ix86_expand_trunc (operands[0], operands[1]);
15399       else
15400         ix86_expand_truncdf_32 (operands[0], operands[1]);
15401     }
15402   else
15403     {
15404       rtx op0, op1;
15405
15406       if (optimize_insn_for_size_p ())
15407         FAIL;
15408
15409       op0 = gen_reg_rtx (XFmode);
15410       op1 = gen_reg_rtx (XFmode);
15411       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15412       emit_insn (gen_frndintxf2_trunc (op0, op1));
15413
15414       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15415     }
15416   DONE;
15417 })
15418
15419 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15420 (define_insn_and_split "frndintxf2_mask_pm"
15421   [(set (match_operand:XF 0 "register_operand" "")
15422         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15423          UNSPEC_FRNDINT_MASK_PM))
15424    (clobber (reg:CC FLAGS_REG))]
15425   "TARGET_USE_FANCY_MATH_387
15426    && flag_unsafe_math_optimizations
15427    && can_create_pseudo_p ()"
15428   "#"
15429   "&& 1"
15430   [(const_int 0)]
15431 {
15432   ix86_optimize_mode_switching[I387_MASK_PM] = 1;
15433
15434   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15435   operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
15436
15437   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
15438                                           operands[2], operands[3]));
15439   DONE;
15440 }
15441   [(set_attr "type" "frndint")
15442    (set_attr "i387_cw" "mask_pm")
15443    (set_attr "mode" "XF")])
15444
15445 (define_insn "frndintxf2_mask_pm_i387"
15446   [(set (match_operand:XF 0 "register_operand" "=f")
15447         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15448          UNSPEC_FRNDINT_MASK_PM))
15449    (use (match_operand:HI 2 "memory_operand" "m"))
15450    (use (match_operand:HI 3 "memory_operand" "m"))]
15451   "TARGET_USE_FANCY_MATH_387
15452    && flag_unsafe_math_optimizations"
15453   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
15454   [(set_attr "type" "frndint")
15455    (set_attr "i387_cw" "mask_pm")
15456    (set_attr "mode" "XF")])
15457
15458 (define_expand "nearbyintxf2"
15459   [(use (match_operand:XF 0 "register_operand" ""))
15460    (use (match_operand:XF 1 "register_operand" ""))]
15461   "TARGET_USE_FANCY_MATH_387
15462    && flag_unsafe_math_optimizations"
15463 {
15464   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
15465   DONE;
15466 })
15467
15468 (define_expand "nearbyint<mode>2"
15469   [(use (match_operand:MODEF 0 "register_operand" ""))
15470    (use (match_operand:MODEF 1 "register_operand" ""))]
15471   "TARGET_USE_FANCY_MATH_387
15472    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15473        || TARGET_MIX_SSE_I387)
15474    && flag_unsafe_math_optimizations"
15475 {
15476   rtx op0 = gen_reg_rtx (XFmode);
15477   rtx op1 = gen_reg_rtx (XFmode);
15478
15479   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15480   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
15481
15482   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15483   DONE;
15484 })
15485
15486 (define_insn "fxam<mode>2_i387"
15487   [(set (match_operand:HI 0 "register_operand" "=a")
15488         (unspec:HI
15489           [(match_operand:X87MODEF 1 "register_operand" "f")]
15490           UNSPEC_FXAM))]
15491   "TARGET_USE_FANCY_MATH_387"
15492   "fxam\n\tfnstsw\t%0"
15493   [(set_attr "type" "multi")
15494    (set_attr "length" "4")
15495    (set_attr "unit" "i387")
15496    (set_attr "mode" "<MODE>")])
15497
15498 (define_insn_and_split "fxam<mode>2_i387_with_temp"
15499   [(set (match_operand:HI 0 "register_operand" "")
15500         (unspec:HI
15501           [(match_operand:MODEF 1 "memory_operand" "")]
15502           UNSPEC_FXAM_MEM))]
15503   "TARGET_USE_FANCY_MATH_387
15504    && can_create_pseudo_p ()"
15505   "#"
15506   "&& 1"
15507   [(set (match_dup 2)(match_dup 1))
15508    (set (match_dup 0)
15509         (unspec:HI [(match_dup 2)] UNSPEC_FXAM))]
15510 {
15511   operands[2] = gen_reg_rtx (<MODE>mode);
15512
15513   MEM_VOLATILE_P (operands[1]) = 1;
15514 }
15515   [(set_attr "type" "multi")
15516    (set_attr "unit" "i387")
15517    (set_attr "mode" "<MODE>")])
15518
15519 (define_expand "isinfxf2"
15520   [(use (match_operand:SI 0 "register_operand" ""))
15521    (use (match_operand:XF 1 "register_operand" ""))]
15522   "TARGET_USE_FANCY_MATH_387
15523    && TARGET_C99_FUNCTIONS"
15524 {
15525   rtx mask = GEN_INT (0x45);
15526   rtx val = GEN_INT (0x05);
15527
15528   rtx cond;
15529
15530   rtx scratch = gen_reg_rtx (HImode);
15531   rtx res = gen_reg_rtx (QImode);
15532
15533   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
15534
15535   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
15536   emit_insn (gen_cmpqi_ext_3 (scratch, val));
15537   cond = gen_rtx_fmt_ee (EQ, QImode,
15538                          gen_rtx_REG (CCmode, FLAGS_REG),
15539                          const0_rtx);
15540   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
15541   emit_insn (gen_zero_extendqisi2 (operands[0], res));
15542   DONE;
15543 })
15544
15545 (define_expand "isinf<mode>2"
15546   [(use (match_operand:SI 0 "register_operand" ""))
15547    (use (match_operand:MODEF 1 "nonimmediate_operand" ""))]
15548   "TARGET_USE_FANCY_MATH_387
15549    && TARGET_C99_FUNCTIONS
15550    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
15551 {
15552   rtx mask = GEN_INT (0x45);
15553   rtx val = GEN_INT (0x05);
15554
15555   rtx cond;
15556
15557   rtx scratch = gen_reg_rtx (HImode);
15558   rtx res = gen_reg_rtx (QImode);
15559
15560   /* Remove excess precision by forcing value through memory. */
15561   if (memory_operand (operands[1], VOIDmode))
15562     emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, operands[1]));
15563   else
15564     {
15565       enum ix86_stack_slot slot = (virtuals_instantiated
15566                                    ? SLOT_TEMP
15567                                    : SLOT_VIRTUAL);
15568       rtx temp = assign_386_stack_local (<MODE>mode, slot);
15569
15570       emit_move_insn (temp, operands[1]);
15571       emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, temp));
15572     }
15573
15574   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
15575   emit_insn (gen_cmpqi_ext_3 (scratch, val));
15576   cond = gen_rtx_fmt_ee (EQ, QImode,
15577                          gen_rtx_REG (CCmode, FLAGS_REG),
15578                          const0_rtx);
15579   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
15580   emit_insn (gen_zero_extendqisi2 (operands[0], res));
15581   DONE;
15582 })
15583
15584 (define_expand "signbitxf2"
15585   [(use (match_operand:SI 0 "register_operand" ""))
15586    (use (match_operand:XF 1 "register_operand" ""))]
15587   "TARGET_USE_FANCY_MATH_387"
15588 {
15589   rtx scratch = gen_reg_rtx (HImode);
15590
15591   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
15592   emit_insn (gen_andsi3 (operands[0],
15593              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15594   DONE;
15595 })
15596
15597 (define_insn "movmsk_df"
15598   [(set (match_operand:SI 0 "register_operand" "=r")
15599         (unspec:SI
15600           [(match_operand:DF 1 "register_operand" "x")]
15601           UNSPEC_MOVMSK))]
15602   "SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH"
15603   "%vmovmskpd\t{%1, %0|%0, %1}"
15604   [(set_attr "type" "ssemov")
15605    (set_attr "prefix" "maybe_vex")
15606    (set_attr "mode" "DF")])
15607
15608 ;; Use movmskpd in SSE mode to avoid store forwarding stall
15609 ;; for 32bit targets and movq+shrq sequence for 64bit targets.
15610 (define_expand "signbitdf2"
15611   [(use (match_operand:SI 0 "register_operand" ""))
15612    (use (match_operand:DF 1 "register_operand" ""))]
15613   "TARGET_USE_FANCY_MATH_387
15614    || (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)"
15615 {
15616   if (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)
15617     {
15618       emit_insn (gen_movmsk_df (operands[0], operands[1]));
15619       emit_insn (gen_andsi3 (operands[0], operands[0], const1_rtx));
15620     }
15621   else
15622     {
15623       rtx scratch = gen_reg_rtx (HImode);
15624
15625       emit_insn (gen_fxamdf2_i387 (scratch, operands[1]));
15626       emit_insn (gen_andsi3 (operands[0],
15627                  gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15628     }
15629   DONE;
15630 })
15631
15632 (define_expand "signbitsf2"
15633   [(use (match_operand:SI 0 "register_operand" ""))
15634    (use (match_operand:SF 1 "register_operand" ""))]
15635   "TARGET_USE_FANCY_MATH_387
15636    && !(SSE_FLOAT_MODE_P (SFmode) && TARGET_SSE_MATH)"
15637 {
15638   rtx scratch = gen_reg_rtx (HImode);
15639
15640   emit_insn (gen_fxamsf2_i387 (scratch, operands[1]));
15641   emit_insn (gen_andsi3 (operands[0],
15642              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15643   DONE;
15644 })
15645 \f
15646 ;; Block operation instructions
15647
15648 (define_insn "cld"
15649   [(unspec_volatile [(const_int 0)] UNSPECV_CLD)]
15650   ""
15651   "cld"
15652   [(set_attr "length" "1")
15653    (set_attr "length_immediate" "0")
15654    (set_attr "modrm" "0")])
15655
15656 (define_expand "movmem<mode>"
15657   [(use (match_operand:BLK 0 "memory_operand" ""))
15658    (use (match_operand:BLK 1 "memory_operand" ""))
15659    (use (match_operand:SWI48 2 "nonmemory_operand" ""))
15660    (use (match_operand:SWI48 3 "const_int_operand" ""))
15661    (use (match_operand:SI 4 "const_int_operand" ""))
15662    (use (match_operand:SI 5 "const_int_operand" ""))]
15663   ""
15664 {
15665  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
15666                          operands[4], operands[5]))
15667    DONE;
15668  else
15669    FAIL;
15670 })
15671
15672 ;; Most CPUs don't like single string operations
15673 ;; Handle this case here to simplify previous expander.
15674
15675 (define_expand "strmov"
15676   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
15677    (set (match_operand 1 "memory_operand" "") (match_dup 4))
15678    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
15679               (clobber (reg:CC FLAGS_REG))])
15680    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
15681               (clobber (reg:CC FLAGS_REG))])]
15682   ""
15683 {
15684   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
15685
15686   /* If .md ever supports :P for Pmode, these can be directly
15687      in the pattern above.  */
15688   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
15689   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
15690
15691   /* Can't use this if the user has appropriated esi or edi.  */
15692   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15693       && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
15694     {
15695       emit_insn (gen_strmov_singleop (operands[0], operands[1],
15696                                       operands[2], operands[3],
15697                                       operands[5], operands[6]));
15698       DONE;
15699     }
15700
15701   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
15702 })
15703
15704 (define_expand "strmov_singleop"
15705   [(parallel [(set (match_operand 1 "memory_operand" "")
15706                    (match_operand 3 "memory_operand" ""))
15707               (set (match_operand 0 "register_operand" "")
15708                    (match_operand 4 "" ""))
15709               (set (match_operand 2 "register_operand" "")
15710                    (match_operand 5 "" ""))])]
15711   ""
15712   "ix86_current_function_needs_cld = 1;")
15713
15714 (define_insn "*strmovdi_rex_1"
15715   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
15716         (mem:DI (match_operand:DI 3 "register_operand" "1")))
15717    (set (match_operand:DI 0 "register_operand" "=D")
15718         (plus:DI (match_dup 2)
15719                  (const_int 8)))
15720    (set (match_operand:DI 1 "register_operand" "=S")
15721         (plus:DI (match_dup 3)
15722                  (const_int 8)))]
15723   "TARGET_64BIT
15724    && !(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15725   "movsq"
15726   [(set_attr "type" "str")
15727    (set_attr "memory" "both")
15728    (set_attr "mode" "DI")])
15729
15730 (define_insn "*strmovsi_1"
15731   [(set (mem:SI (match_operand:P 2 "register_operand" "0"))
15732         (mem:SI (match_operand:P 3 "register_operand" "1")))
15733    (set (match_operand:P 0 "register_operand" "=D")
15734         (plus:P (match_dup 2)
15735                 (const_int 4)))
15736    (set (match_operand:P 1 "register_operand" "=S")
15737         (plus:P (match_dup 3)
15738                 (const_int 4)))]
15739   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15740   "movs{l|d}"
15741   [(set_attr "type" "str")
15742    (set_attr "memory" "both")
15743    (set_attr "mode" "SI")])
15744
15745 (define_insn "*strmovhi_1"
15746   [(set (mem:HI (match_operand:P 2 "register_operand" "0"))
15747         (mem:HI (match_operand:P 3 "register_operand" "1")))
15748    (set (match_operand:P 0 "register_operand" "=D")
15749         (plus:P (match_dup 2)
15750                 (const_int 2)))
15751    (set (match_operand:P 1 "register_operand" "=S")
15752         (plus:P (match_dup 3)
15753                 (const_int 2)))]
15754   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15755   "movsw"
15756   [(set_attr "type" "str")
15757    (set_attr "memory" "both")
15758    (set_attr "mode" "HI")])
15759
15760 (define_insn "*strmovqi_1"
15761   [(set (mem:QI (match_operand:P 2 "register_operand" "0"))
15762         (mem:QI (match_operand:P 3 "register_operand" "1")))
15763    (set (match_operand:P 0 "register_operand" "=D")
15764         (plus:P (match_dup 2)
15765                 (const_int 1)))
15766    (set (match_operand:P 1 "register_operand" "=S")
15767         (plus:P (match_dup 3)
15768                 (const_int 1)))]
15769   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15770   "movsb"
15771   [(set_attr "type" "str")
15772    (set_attr "memory" "both")
15773    (set (attr "prefix_rex")
15774         (if_then_else
15775           (match_test "<P:MODE>mode == DImode")
15776           (const_string "0")
15777           (const_string "*")))
15778    (set_attr "mode" "QI")])
15779
15780 (define_expand "rep_mov"
15781   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
15782               (set (match_operand 0 "register_operand" "")
15783                    (match_operand 5 "" ""))
15784               (set (match_operand 2 "register_operand" "")
15785                    (match_operand 6 "" ""))
15786               (set (match_operand 1 "memory_operand" "")
15787                    (match_operand 3 "memory_operand" ""))
15788               (use (match_dup 4))])]
15789   ""
15790   "ix86_current_function_needs_cld = 1;")
15791
15792 (define_insn "*rep_movdi_rex64"
15793   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15794    (set (match_operand:DI 0 "register_operand" "=D")
15795         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
15796                             (const_int 3))
15797                  (match_operand:DI 3 "register_operand" "0")))
15798    (set (match_operand:DI 1 "register_operand" "=S")
15799         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
15800                  (match_operand:DI 4 "register_operand" "1")))
15801    (set (mem:BLK (match_dup 3))
15802         (mem:BLK (match_dup 4)))
15803    (use (match_dup 5))]
15804   "TARGET_64BIT
15805    && !(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15806   "rep{%;} movsq"
15807   [(set_attr "type" "str")
15808    (set_attr "prefix_rep" "1")
15809    (set_attr "memory" "both")
15810    (set_attr "mode" "DI")])
15811
15812 (define_insn "*rep_movsi"
15813   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15814    (set (match_operand:P 0 "register_operand" "=D")
15815         (plus:P (ashift:P (match_operand:P 5 "register_operand" "2")
15816                           (const_int 2))
15817                  (match_operand:P 3 "register_operand" "0")))
15818    (set (match_operand:P 1 "register_operand" "=S")
15819         (plus:P (ashift:P (match_dup 5) (const_int 2))
15820                 (match_operand:P 4 "register_operand" "1")))
15821    (set (mem:BLK (match_dup 3))
15822         (mem:BLK (match_dup 4)))
15823    (use (match_dup 5))]
15824   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15825   "rep{%;} movs{l|d}"
15826   [(set_attr "type" "str")
15827    (set_attr "prefix_rep" "1")
15828    (set_attr "memory" "both")
15829    (set_attr "mode" "SI")])
15830
15831 (define_insn "*rep_movqi"
15832   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15833    (set (match_operand:P 0 "register_operand" "=D")
15834         (plus:P (match_operand:P 3 "register_operand" "0")
15835                 (match_operand:P 5 "register_operand" "2")))
15836    (set (match_operand:P 1 "register_operand" "=S")
15837         (plus:P (match_operand:P 4 "register_operand" "1") (match_dup 5)))
15838    (set (mem:BLK (match_dup 3))
15839         (mem:BLK (match_dup 4)))
15840    (use (match_dup 5))]
15841   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15842   "rep{%;} movsb"
15843   [(set_attr "type" "str")
15844    (set_attr "prefix_rep" "1")
15845    (set_attr "memory" "both")
15846    (set_attr "mode" "QI")])
15847
15848 (define_expand "setmem<mode>"
15849    [(use (match_operand:BLK 0 "memory_operand" ""))
15850     (use (match_operand:SWI48 1 "nonmemory_operand" ""))
15851     (use (match_operand:QI 2 "nonmemory_operand" ""))
15852     (use (match_operand 3 "const_int_operand" ""))
15853     (use (match_operand:SI 4 "const_int_operand" ""))
15854     (use (match_operand:SI 5 "const_int_operand" ""))]
15855   ""
15856 {
15857  if (ix86_expand_setmem (operands[0], operands[1],
15858                          operands[2], operands[3],
15859                          operands[4], operands[5]))
15860    DONE;
15861  else
15862    FAIL;
15863 })
15864
15865 ;; Most CPUs don't like single string operations
15866 ;; Handle this case here to simplify previous expander.
15867
15868 (define_expand "strset"
15869   [(set (match_operand 1 "memory_operand" "")
15870         (match_operand 2 "register_operand" ""))
15871    (parallel [(set (match_operand 0 "register_operand" "")
15872                    (match_dup 3))
15873               (clobber (reg:CC FLAGS_REG))])]
15874   ""
15875 {
15876   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
15877     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
15878
15879   /* If .md ever supports :P for Pmode, this can be directly
15880      in the pattern above.  */
15881   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
15882                               GEN_INT (GET_MODE_SIZE (GET_MODE
15883                                                       (operands[2]))));
15884   /* Can't use this if the user has appropriated eax or edi.  */
15885   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15886       && !(fixed_regs[AX_REG] || fixed_regs[DI_REG]))
15887     {
15888       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
15889                                       operands[3]));
15890       DONE;
15891     }
15892 })
15893
15894 (define_expand "strset_singleop"
15895   [(parallel [(set (match_operand 1 "memory_operand" "")
15896                    (match_operand 2 "register_operand" ""))
15897               (set (match_operand 0 "register_operand" "")
15898                    (match_operand 3 "" ""))])]
15899   ""
15900   "ix86_current_function_needs_cld = 1;")
15901
15902 (define_insn "*strsetdi_rex_1"
15903   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
15904         (match_operand:DI 2 "register_operand" "a"))
15905    (set (match_operand:DI 0 "register_operand" "=D")
15906         (plus:DI (match_dup 1)
15907                  (const_int 8)))]
15908   "TARGET_64BIT
15909    && !(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15910   "stosq"
15911   [(set_attr "type" "str")
15912    (set_attr "memory" "store")
15913    (set_attr "mode" "DI")])
15914
15915 (define_insn "*strsetsi_1"
15916   [(set (mem:SI (match_operand:P 1 "register_operand" "0"))
15917         (match_operand:SI 2 "register_operand" "a"))
15918    (set (match_operand:P 0 "register_operand" "=D")
15919         (plus:P (match_dup 1)
15920                 (const_int 4)))]
15921   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15922   "stos{l|d}"
15923   [(set_attr "type" "str")
15924    (set_attr "memory" "store")
15925    (set_attr "mode" "SI")])
15926
15927 (define_insn "*strsethi_1"
15928   [(set (mem:HI (match_operand:P 1 "register_operand" "0"))
15929         (match_operand:HI 2 "register_operand" "a"))
15930    (set (match_operand:P 0 "register_operand" "=D")
15931         (plus:P (match_dup 1)
15932                 (const_int 2)))]
15933   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15934   "stosw"
15935   [(set_attr "type" "str")
15936    (set_attr "memory" "store")
15937    (set_attr "mode" "HI")])
15938
15939 (define_insn "*strsetqi_1"
15940   [(set (mem:QI (match_operand:P 1 "register_operand" "0"))
15941         (match_operand:QI 2 "register_operand" "a"))
15942    (set (match_operand:P 0 "register_operand" "=D")
15943         (plus:P (match_dup 1)
15944                 (const_int 1)))]
15945   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15946   "stosb"
15947   [(set_attr "type" "str")
15948    (set_attr "memory" "store")
15949    (set (attr "prefix_rex")
15950         (if_then_else
15951           (match_test "<P:MODE>mode == DImode")
15952           (const_string "0")
15953           (const_string "*")))
15954    (set_attr "mode" "QI")])
15955
15956 (define_expand "rep_stos"
15957   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
15958               (set (match_operand 0 "register_operand" "")
15959                    (match_operand 4 "" ""))
15960               (set (match_operand 2 "memory_operand" "") (const_int 0))
15961               (use (match_operand 3 "register_operand" ""))
15962               (use (match_dup 1))])]
15963   ""
15964   "ix86_current_function_needs_cld = 1;")
15965
15966 (define_insn "*rep_stosdi_rex64"
15967   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15968    (set (match_operand:DI 0 "register_operand" "=D")
15969         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
15970                             (const_int 3))
15971                  (match_operand:DI 3 "register_operand" "0")))
15972    (set (mem:BLK (match_dup 3))
15973         (const_int 0))
15974    (use (match_operand:DI 2 "register_operand" "a"))
15975    (use (match_dup 4))]
15976   "TARGET_64BIT
15977    && !(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
15978   "rep{%;} stosq"
15979   [(set_attr "type" "str")
15980    (set_attr "prefix_rep" "1")
15981    (set_attr "memory" "store")
15982    (set_attr "mode" "DI")])
15983
15984 (define_insn "*rep_stossi"
15985   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
15986    (set (match_operand:P 0 "register_operand" "=D")
15987         (plus:P (ashift:P (match_operand:P 4 "register_operand" "1")
15988                           (const_int 2))
15989                  (match_operand:P 3 "register_operand" "0")))
15990    (set (mem:BLK (match_dup 3))
15991         (const_int 0))
15992    (use (match_operand:SI 2 "register_operand" "a"))
15993    (use (match_dup 4))]
15994   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
15995   "rep{%;} stos{l|d}"
15996   [(set_attr "type" "str")
15997    (set_attr "prefix_rep" "1")
15998    (set_attr "memory" "store")
15999    (set_attr "mode" "SI")])
16000
16001 (define_insn "*rep_stosqi"
16002   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
16003    (set (match_operand:P 0 "register_operand" "=D")
16004         (plus:P (match_operand:P 3 "register_operand" "0")
16005                 (match_operand:P 4 "register_operand" "1")))
16006    (set (mem:BLK (match_dup 3))
16007         (const_int 0))
16008    (use (match_operand:QI 2 "register_operand" "a"))
16009    (use (match_dup 4))]
16010   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16011   "rep{%;} stosb"
16012   [(set_attr "type" "str")
16013    (set_attr "prefix_rep" "1")
16014    (set_attr "memory" "store")
16015    (set (attr "prefix_rex")
16016         (if_then_else
16017           (match_test "<P:MODE>mode == DImode")
16018           (const_string "0")
16019           (const_string "*")))
16020    (set_attr "mode" "QI")])
16021
16022 (define_expand "cmpstrnsi"
16023   [(set (match_operand:SI 0 "register_operand" "")
16024         (compare:SI (match_operand:BLK 1 "general_operand" "")
16025                     (match_operand:BLK 2 "general_operand" "")))
16026    (use (match_operand 3 "general_operand" ""))
16027    (use (match_operand 4 "immediate_operand" ""))]
16028   ""
16029 {
16030   rtx addr1, addr2, out, outlow, count, countreg, align;
16031
16032   if (optimize_insn_for_size_p () && !TARGET_INLINE_ALL_STRINGOPS)
16033     FAIL;
16034
16035   /* Can't use this if the user has appropriated ecx, esi or edi.  */
16036   if (fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])
16037     FAIL;
16038
16039   out = operands[0];
16040   if (!REG_P (out))
16041     out = gen_reg_rtx (SImode);
16042
16043   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
16044   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
16045   if (addr1 != XEXP (operands[1], 0))
16046     operands[1] = replace_equiv_address_nv (operands[1], addr1);
16047   if (addr2 != XEXP (operands[2], 0))
16048     operands[2] = replace_equiv_address_nv (operands[2], addr2);
16049
16050   count = operands[3];
16051   countreg = ix86_zero_extend_to_Pmode (count);
16052
16053   /* %%% Iff we are testing strict equality, we can use known alignment
16054      to good advantage.  This may be possible with combine, particularly
16055      once cc0 is dead.  */
16056   align = operands[4];
16057
16058   if (CONST_INT_P (count))
16059     {
16060       if (INTVAL (count) == 0)
16061         {
16062           emit_move_insn (operands[0], const0_rtx);
16063           DONE;
16064         }
16065       emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
16066                                      operands[1], operands[2]));
16067     }
16068   else
16069     {
16070       rtx (*gen_cmp) (rtx, rtx);
16071
16072       gen_cmp = (TARGET_64BIT
16073                  ? gen_cmpdi_1 : gen_cmpsi_1);
16074
16075       emit_insn (gen_cmp (countreg, countreg));
16076       emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
16077                                   operands[1], operands[2]));
16078     }
16079
16080   outlow = gen_lowpart (QImode, out);
16081   emit_insn (gen_cmpintqi (outlow));
16082   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
16083
16084   if (operands[0] != out)
16085     emit_move_insn (operands[0], out);
16086
16087   DONE;
16088 })
16089
16090 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
16091
16092 (define_expand "cmpintqi"
16093   [(set (match_dup 1)
16094         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16095    (set (match_dup 2)
16096         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16097    (parallel [(set (match_operand:QI 0 "register_operand" "")
16098                    (minus:QI (match_dup 1)
16099                              (match_dup 2)))
16100               (clobber (reg:CC FLAGS_REG))])]
16101   ""
16102 {
16103   operands[1] = gen_reg_rtx (QImode);
16104   operands[2] = gen_reg_rtx (QImode);
16105 })
16106
16107 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
16108 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
16109
16110 (define_expand "cmpstrnqi_nz_1"
16111   [(parallel [(set (reg:CC FLAGS_REG)
16112                    (compare:CC (match_operand 4 "memory_operand" "")
16113                                (match_operand 5 "memory_operand" "")))
16114               (use (match_operand 2 "register_operand" ""))
16115               (use (match_operand:SI 3 "immediate_operand" ""))
16116               (clobber (match_operand 0 "register_operand" ""))
16117               (clobber (match_operand 1 "register_operand" ""))
16118               (clobber (match_dup 2))])]
16119   ""
16120   "ix86_current_function_needs_cld = 1;")
16121
16122 (define_insn "*cmpstrnqi_nz_1"
16123   [(set (reg:CC FLAGS_REG)
16124         (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16125                     (mem:BLK (match_operand:P 5 "register_operand" "1"))))
16126    (use (match_operand:P 6 "register_operand" "2"))
16127    (use (match_operand:SI 3 "immediate_operand" "i"))
16128    (clobber (match_operand:P 0 "register_operand" "=S"))
16129    (clobber (match_operand:P 1 "register_operand" "=D"))
16130    (clobber (match_operand:P 2 "register_operand" "=c"))]
16131   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16132   "repz{%;} cmpsb"
16133   [(set_attr "type" "str")
16134    (set_attr "mode" "QI")
16135    (set (attr "prefix_rex")
16136         (if_then_else
16137           (match_test "<P:MODE>mode == DImode")
16138           (const_string "0")
16139           (const_string "*")))
16140    (set_attr "prefix_rep" "1")])
16141
16142 ;; The same, but the count is not known to not be zero.
16143
16144 (define_expand "cmpstrnqi_1"
16145   [(parallel [(set (reg:CC FLAGS_REG)
16146                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
16147                                      (const_int 0))
16148                   (compare:CC (match_operand 4 "memory_operand" "")
16149                               (match_operand 5 "memory_operand" ""))
16150                   (const_int 0)))
16151               (use (match_operand:SI 3 "immediate_operand" ""))
16152               (use (reg:CC FLAGS_REG))
16153               (clobber (match_operand 0 "register_operand" ""))
16154               (clobber (match_operand 1 "register_operand" ""))
16155               (clobber (match_dup 2))])]
16156   ""
16157   "ix86_current_function_needs_cld = 1;")
16158
16159 (define_insn "*cmpstrnqi_1"
16160   [(set (reg:CC FLAGS_REG)
16161         (if_then_else:CC (ne (match_operand:P 6 "register_operand" "2")
16162                              (const_int 0))
16163           (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16164                       (mem:BLK (match_operand:P 5 "register_operand" "1")))
16165           (const_int 0)))
16166    (use (match_operand:SI 3 "immediate_operand" "i"))
16167    (use (reg:CC FLAGS_REG))
16168    (clobber (match_operand:P 0 "register_operand" "=S"))
16169    (clobber (match_operand:P 1 "register_operand" "=D"))
16170    (clobber (match_operand:P 2 "register_operand" "=c"))]
16171   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16172   "repz{%;} cmpsb"
16173   [(set_attr "type" "str")
16174    (set_attr "mode" "QI")
16175    (set (attr "prefix_rex")
16176         (if_then_else
16177           (match_test "<P:MODE>mode == DImode")
16178           (const_string "0")
16179           (const_string "*")))
16180    (set_attr "prefix_rep" "1")])
16181
16182 (define_expand "strlen<mode>"
16183   [(set (match_operand:P 0 "register_operand" "")
16184         (unspec:P [(match_operand:BLK 1 "general_operand" "")
16185                    (match_operand:QI 2 "immediate_operand" "")
16186                    (match_operand 3 "immediate_operand" "")]
16187                   UNSPEC_SCAS))]
16188   ""
16189 {
16190  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
16191    DONE;
16192  else
16193    FAIL;
16194 })
16195
16196 (define_expand "strlenqi_1"
16197   [(parallel [(set (match_operand 0 "register_operand" "")
16198                    (match_operand 2 "" ""))
16199               (clobber (match_operand 1 "register_operand" ""))
16200               (clobber (reg:CC FLAGS_REG))])]
16201   ""
16202   "ix86_current_function_needs_cld = 1;")
16203
16204 (define_insn "*strlenqi_1"
16205   [(set (match_operand:P 0 "register_operand" "=&c")
16206         (unspec:P [(mem:BLK (match_operand:P 5 "register_operand" "1"))
16207                    (match_operand:QI 2 "register_operand" "a")
16208                    (match_operand:P 3 "immediate_operand" "i")
16209                    (match_operand:P 4 "register_operand" "0")] UNSPEC_SCAS))
16210    (clobber (match_operand:P 1 "register_operand" "=D"))
16211    (clobber (reg:CC FLAGS_REG))]
16212   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16213   "repnz{%;} scasb"
16214   [(set_attr "type" "str")
16215    (set_attr "mode" "QI")
16216    (set (attr "prefix_rex")
16217         (if_then_else
16218           (match_test "<P:MODE>mode == DImode")
16219           (const_string "0")
16220           (const_string "*")))
16221    (set_attr "prefix_rep" "1")])
16222
16223 ;; Peephole optimizations to clean up after cmpstrn*.  This should be
16224 ;; handled in combine, but it is not currently up to the task.
16225 ;; When used for their truth value, the cmpstrn* expanders generate
16226 ;; code like this:
16227 ;;
16228 ;;   repz cmpsb
16229 ;;   seta       %al
16230 ;;   setb       %dl
16231 ;;   cmpb       %al, %dl
16232 ;;   jcc        label
16233 ;;
16234 ;; The intermediate three instructions are unnecessary.
16235
16236 ;; This one handles cmpstrn*_nz_1...
16237 (define_peephole2
16238   [(parallel[
16239      (set (reg:CC FLAGS_REG)
16240           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16241                       (mem:BLK (match_operand 5 "register_operand" ""))))
16242      (use (match_operand 6 "register_operand" ""))
16243      (use (match_operand:SI 3 "immediate_operand" ""))
16244      (clobber (match_operand 0 "register_operand" ""))
16245      (clobber (match_operand 1 "register_operand" ""))
16246      (clobber (match_operand 2 "register_operand" ""))])
16247    (set (match_operand:QI 7 "register_operand" "")
16248         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16249    (set (match_operand:QI 8 "register_operand" "")
16250         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16251    (set (reg FLAGS_REG)
16252         (compare (match_dup 7) (match_dup 8)))
16253   ]
16254   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16255   [(parallel[
16256      (set (reg:CC FLAGS_REG)
16257           (compare:CC (mem:BLK (match_dup 4))
16258                       (mem:BLK (match_dup 5))))
16259      (use (match_dup 6))
16260      (use (match_dup 3))
16261      (clobber (match_dup 0))
16262      (clobber (match_dup 1))
16263      (clobber (match_dup 2))])])
16264
16265 ;; ...and this one handles cmpstrn*_1.
16266 (define_peephole2
16267   [(parallel[
16268      (set (reg:CC FLAGS_REG)
16269           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
16270                                (const_int 0))
16271             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16272                         (mem:BLK (match_operand 5 "register_operand" "")))
16273             (const_int 0)))
16274      (use (match_operand:SI 3 "immediate_operand" ""))
16275      (use (reg:CC FLAGS_REG))
16276      (clobber (match_operand 0 "register_operand" ""))
16277      (clobber (match_operand 1 "register_operand" ""))
16278      (clobber (match_operand 2 "register_operand" ""))])
16279    (set (match_operand:QI 7 "register_operand" "")
16280         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16281    (set (match_operand:QI 8 "register_operand" "")
16282         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16283    (set (reg FLAGS_REG)
16284         (compare (match_dup 7) (match_dup 8)))
16285   ]
16286   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16287   [(parallel[
16288      (set (reg:CC FLAGS_REG)
16289           (if_then_else:CC (ne (match_dup 6)
16290                                (const_int 0))
16291             (compare:CC (mem:BLK (match_dup 4))
16292                         (mem:BLK (match_dup 5)))
16293             (const_int 0)))
16294      (use (match_dup 3))
16295      (use (reg:CC FLAGS_REG))
16296      (clobber (match_dup 0))
16297      (clobber (match_dup 1))
16298      (clobber (match_dup 2))])])
16299 \f
16300 ;; Conditional move instructions.
16301
16302 (define_expand "mov<mode>cc"
16303   [(set (match_operand:SWIM 0 "register_operand" "")
16304         (if_then_else:SWIM (match_operand 1 "ordered_comparison_operator" "")
16305                            (match_operand:SWIM 2 "<general_operand>" "")
16306                            (match_operand:SWIM 3 "<general_operand>" "")))]
16307   ""
16308   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
16309
16310 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
16311 ;; the register first winds up with `sbbl $0,reg', which is also weird.
16312 ;; So just document what we're doing explicitly.
16313
16314 (define_expand "x86_mov<mode>cc_0_m1"
16315   [(parallel
16316     [(set (match_operand:SWI48 0 "register_operand" "")
16317           (if_then_else:SWI48
16318             (match_operator:SWI48 2 "ix86_carry_flag_operator"
16319              [(match_operand 1 "flags_reg_operand" "")
16320               (const_int 0)])
16321             (const_int -1)
16322             (const_int 0)))
16323      (clobber (reg:CC FLAGS_REG))])])
16324
16325 (define_insn "*x86_mov<mode>cc_0_m1"
16326   [(set (match_operand:SWI48 0 "register_operand" "=r")
16327         (if_then_else:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16328                              [(reg FLAGS_REG) (const_int 0)])
16329           (const_int -1)
16330           (const_int 0)))
16331    (clobber (reg:CC FLAGS_REG))]
16332   ""
16333   "sbb{<imodesuffix>}\t%0, %0"
16334   ; Since we don't have the proper number of operands for an alu insn,
16335   ; fill in all the blanks.
16336   [(set_attr "type" "alu")
16337    (set_attr "use_carry" "1")
16338    (set_attr "pent_pair" "pu")
16339    (set_attr "memory" "none")
16340    (set_attr "imm_disp" "false")
16341    (set_attr "mode" "<MODE>")
16342    (set_attr "length_immediate" "0")])
16343
16344 (define_insn "*x86_mov<mode>cc_0_m1_se"
16345   [(set (match_operand:SWI48 0 "register_operand" "=r")
16346         (sign_extract:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16347                              [(reg FLAGS_REG) (const_int 0)])
16348                             (const_int 1)
16349                             (const_int 0)))
16350    (clobber (reg:CC FLAGS_REG))]
16351   ""
16352   "sbb{<imodesuffix>}\t%0, %0"
16353   [(set_attr "type" "alu")
16354    (set_attr "use_carry" "1")
16355    (set_attr "pent_pair" "pu")
16356    (set_attr "memory" "none")
16357    (set_attr "imm_disp" "false")
16358    (set_attr "mode" "<MODE>")
16359    (set_attr "length_immediate" "0")])
16360
16361 (define_insn "*x86_mov<mode>cc_0_m1_neg"
16362   [(set (match_operand:SWI48 0 "register_operand" "=r")
16363         (neg:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16364                     [(reg FLAGS_REG) (const_int 0)])))
16365    (clobber (reg:CC FLAGS_REG))]
16366   ""
16367   "sbb{<imodesuffix>}\t%0, %0"
16368   [(set_attr "type" "alu")
16369    (set_attr "use_carry" "1")
16370    (set_attr "pent_pair" "pu")
16371    (set_attr "memory" "none")
16372    (set_attr "imm_disp" "false")
16373    (set_attr "mode" "<MODE>")
16374    (set_attr "length_immediate" "0")])
16375
16376 (define_insn "*mov<mode>cc_noc"
16377   [(set (match_operand:SWI248 0 "register_operand" "=r,r")
16378         (if_then_else:SWI248 (match_operator 1 "ix86_comparison_operator"
16379                                [(reg FLAGS_REG) (const_int 0)])
16380           (match_operand:SWI248 2 "nonimmediate_operand" "rm,0")
16381           (match_operand:SWI248 3 "nonimmediate_operand" "0,rm")))]
16382   "TARGET_CMOVE && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16383   "@
16384    cmov%O2%C1\t{%2, %0|%0, %2}
16385    cmov%O2%c1\t{%3, %0|%0, %3}"
16386   [(set_attr "type" "icmov")
16387    (set_attr "mode" "<MODE>")])
16388
16389 (define_insn "*movqicc_noc"
16390   [(set (match_operand:QI 0 "register_operand" "=r,r")
16391         (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
16392                            [(reg FLAGS_REG) (const_int 0)])
16393                       (match_operand:QI 2 "register_operand" "r,0")
16394                       (match_operand:QI 3 "register_operand" "0,r")))]
16395   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
16396   "#"
16397   [(set_attr "type" "icmov")
16398    (set_attr "mode" "QI")])
16399
16400 (define_split
16401   [(set (match_operand 0 "register_operand")
16402         (if_then_else (match_operator 1 "ix86_comparison_operator"
16403                         [(reg FLAGS_REG) (const_int 0)])
16404                       (match_operand 2 "register_operand")
16405                       (match_operand 3 "register_operand")))]
16406   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL
16407    && (GET_MODE (operands[0]) == QImode
16408        || GET_MODE (operands[0]) == HImode)
16409    && reload_completed"
16410   [(set (match_dup 0)
16411         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
16412 {
16413   operands[0] = gen_lowpart (SImode, operands[0]);
16414   operands[2] = gen_lowpart (SImode, operands[2]);
16415   operands[3] = gen_lowpart (SImode, operands[3]);
16416 })
16417
16418 (define_expand "mov<mode>cc"
16419   [(set (match_operand:X87MODEF 0 "register_operand" "")
16420         (if_then_else:X87MODEF
16421           (match_operand 1 "ix86_fp_comparison_operator" "")
16422           (match_operand:X87MODEF 2 "register_operand" "")
16423           (match_operand:X87MODEF 3 "register_operand" "")))]
16424   "(TARGET_80387 && TARGET_CMOVE)
16425    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
16426   "if (ix86_expand_fp_movcc (operands)) DONE; else FAIL;")
16427
16428 (define_insn "*movxfcc_1"
16429   [(set (match_operand:XF 0 "register_operand" "=f,f")
16430         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
16431                                 [(reg FLAGS_REG) (const_int 0)])
16432                       (match_operand:XF 2 "register_operand" "f,0")
16433                       (match_operand:XF 3 "register_operand" "0,f")))]
16434   "TARGET_80387 && TARGET_CMOVE"
16435   "@
16436    fcmov%F1\t{%2, %0|%0, %2}
16437    fcmov%f1\t{%3, %0|%0, %3}"
16438   [(set_attr "type" "fcmov")
16439    (set_attr "mode" "XF")])
16440
16441 (define_insn "*movdfcc_1_rex64"
16442   [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
16443         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16444                                 [(reg FLAGS_REG) (const_int 0)])
16445                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16446                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16447   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16448    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16449   "@
16450    fcmov%F1\t{%2, %0|%0, %2}
16451    fcmov%f1\t{%3, %0|%0, %3}
16452    cmov%O2%C1\t{%2, %0|%0, %2}
16453    cmov%O2%c1\t{%3, %0|%0, %3}"
16454   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16455    (set_attr "mode" "DF,DF,DI,DI")])
16456
16457 (define_insn "*movdfcc_1"
16458   [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
16459         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16460                                 [(reg FLAGS_REG) (const_int 0)])
16461                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16462                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16463   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16464    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16465   "@
16466    fcmov%F1\t{%2, %0|%0, %2}
16467    fcmov%f1\t{%3, %0|%0, %3}
16468    #
16469    #"
16470   [(set_attr "type" "fcmov,fcmov,multi,multi")
16471    (set_attr "mode" "DF,DF,DI,DI")])
16472
16473 (define_split
16474   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand")
16475         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16476                                 [(reg FLAGS_REG) (const_int 0)])
16477                       (match_operand:DF 2 "nonimmediate_operand")
16478                       (match_operand:DF 3 "nonimmediate_operand")))]
16479   "!TARGET_64BIT && reload_completed"
16480   [(set (match_dup 2)
16481         (if_then_else:SI (match_dup 1) (match_dup 4) (match_dup 5)))
16482    (set (match_dup 3)
16483         (if_then_else:SI (match_dup 1) (match_dup 6) (match_dup 7)))]
16484 {
16485   split_double_mode (DImode, &operands[2], 2, &operands[4], &operands[6]);
16486   split_double_mode (DImode, &operands[0], 1, &operands[2], &operands[3]);
16487 })
16488
16489 (define_insn "*movsfcc_1_387"
16490   [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
16491         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
16492                                 [(reg FLAGS_REG) (const_int 0)])
16493                       (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
16494                       (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
16495   "TARGET_80387 && TARGET_CMOVE
16496    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16497   "@
16498    fcmov%F1\t{%2, %0|%0, %2}
16499    fcmov%f1\t{%3, %0|%0, %3}
16500    cmov%O2%C1\t{%2, %0|%0, %2}
16501    cmov%O2%c1\t{%3, %0|%0, %3}"
16502   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16503    (set_attr "mode" "SF,SF,SI,SI")])
16504
16505 ;; All moves in XOP pcmov instructions are 128 bits and hence we restrict
16506 ;; the scalar versions to have only XMM registers as operands.
16507
16508 ;; XOP conditional move
16509 (define_insn "*xop_pcmov_<mode>"
16510   [(set (match_operand:MODEF 0 "register_operand" "=x")
16511         (if_then_else:MODEF
16512           (match_operand:MODEF 1 "register_operand" "x")
16513           (match_operand:MODEF 2 "register_operand" "x")
16514           (match_operand:MODEF 3 "register_operand" "x")))]
16515   "TARGET_XOP"
16516   "vpcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
16517   [(set_attr "type" "sse4arg")])
16518
16519 ;; These versions of the min/max patterns are intentionally ignorant of
16520 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
16521 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
16522 ;; are undefined in this condition, we're certain this is correct.
16523
16524 (define_insn "<code><mode>3"
16525   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16526         (smaxmin:MODEF
16527           (match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
16528           (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")))]
16529   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16530   "@
16531    <maxmin_float><ssemodesuffix>\t{%2, %0|%0, %2}
16532    v<maxmin_float><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16533   [(set_attr "isa" "noavx,avx")
16534    (set_attr "prefix" "orig,vex")
16535    (set_attr "type" "sseadd")
16536    (set_attr "mode" "<MODE>")])
16537
16538 ;; These versions of the min/max patterns implement exactly the operations
16539 ;;   min = (op1 < op2 ? op1 : op2)
16540 ;;   max = (!(op1 < op2) ? op1 : op2)
16541 ;; Their operands are not commutative, and thus they may be used in the
16542 ;; presence of -0.0 and NaN.
16543
16544 (define_insn "*ieee_smin<mode>3"
16545   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16546         (unspec:MODEF
16547           [(match_operand:MODEF 1 "register_operand" "0,x")
16548            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16549          UNSPEC_IEEE_MIN))]
16550   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16551   "@
16552    min<ssemodesuffix>\t{%2, %0|%0, %2}
16553    vmin<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16554   [(set_attr "isa" "noavx,avx")
16555    (set_attr "prefix" "orig,vex")
16556    (set_attr "type" "sseadd")
16557    (set_attr "mode" "<MODE>")])
16558
16559 (define_insn "*ieee_smax<mode>3"
16560   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16561         (unspec:MODEF
16562           [(match_operand:MODEF 1 "register_operand" "0,x")
16563            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16564          UNSPEC_IEEE_MAX))]
16565   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16566   "@
16567    max<ssemodesuffix>\t{%2, %0|%0, %2}
16568    vmax<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16569   [(set_attr "isa" "noavx,avx")
16570    (set_attr "prefix" "orig,vex")
16571    (set_attr "type" "sseadd")
16572    (set_attr "mode" "<MODE>")])
16573
16574 ;; Make two stack loads independent:
16575 ;;   fld aa              fld aa
16576 ;;   fld %st(0)     ->   fld bb
16577 ;;   fmul bb             fmul %st(1), %st
16578 ;;
16579 ;; Actually we only match the last two instructions for simplicity.
16580 (define_peephole2
16581   [(set (match_operand 0 "fp_register_operand" "")
16582         (match_operand 1 "fp_register_operand" ""))
16583    (set (match_dup 0)
16584         (match_operator 2 "binary_fp_operator"
16585            [(match_dup 0)
16586             (match_operand 3 "memory_operand" "")]))]
16587   "REGNO (operands[0]) != REGNO (operands[1])"
16588   [(set (match_dup 0) (match_dup 3))
16589    (set (match_dup 0) (match_dup 4))]
16590
16591   ;; The % modifier is not operational anymore in peephole2's, so we have to
16592   ;; swap the operands manually in the case of addition and multiplication.
16593 {
16594   rtx op0, op1;
16595
16596   if (COMMUTATIVE_ARITH_P (operands[2]))
16597     op0 = operands[0], op1 = operands[1];
16598   else
16599     op0 = operands[1], op1 = operands[0];
16600
16601   operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]),
16602                                 GET_MODE (operands[2]),
16603                                 op0, op1);
16604 })
16605
16606 ;; Conditional addition patterns
16607 (define_expand "add<mode>cc"
16608   [(match_operand:SWI 0 "register_operand" "")
16609    (match_operand 1 "ordered_comparison_operator" "")
16610    (match_operand:SWI 2 "register_operand" "")
16611    (match_operand:SWI 3 "const_int_operand" "")]
16612   ""
16613   "if (ix86_expand_int_addcc (operands)) DONE; else FAIL;")
16614 \f
16615 ;; Misc patterns (?)
16616
16617 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
16618 ;; Otherwise there will be nothing to keep
16619 ;;
16620 ;; [(set (reg ebp) (reg esp))]
16621 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
16622 ;;  (clobber (eflags)]
16623 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
16624 ;;
16625 ;; in proper program order.
16626
16627 (define_insn "pro_epilogue_adjust_stack_<mode>_add"
16628   [(set (match_operand:P 0 "register_operand" "=r,r")
16629         (plus:P (match_operand:P 1 "register_operand" "0,r")
16630                 (match_operand:P 2 "<nonmemory_operand>" "r<i>,l<i>")))
16631    (clobber (reg:CC FLAGS_REG))
16632    (clobber (mem:BLK (scratch)))]
16633   ""
16634 {
16635   switch (get_attr_type (insn))
16636     {
16637     case TYPE_IMOV:
16638       return "mov{<imodesuffix>}\t{%1, %0|%0, %1}";
16639
16640     case TYPE_ALU:
16641       gcc_assert (rtx_equal_p (operands[0], operands[1]));
16642       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
16643         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
16644
16645       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
16646
16647     default:
16648       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
16649       return "lea{<imodesuffix>}\t{%E2, %0|%0, %E2}";
16650     }
16651 }
16652   [(set (attr "type")
16653         (cond [(and (eq_attr "alternative" "0")
16654                     (not (match_test "TARGET_OPT_AGU")))
16655                  (const_string "alu")
16656                (match_operand:<MODE> 2 "const0_operand" "")
16657                  (const_string "imov")
16658               ]
16659               (const_string "lea")))
16660    (set (attr "length_immediate")
16661         (cond [(eq_attr "type" "imov")
16662                  (const_string "0")
16663                (and (eq_attr "type" "alu")
16664                     (match_operand 2 "const128_operand" ""))
16665                  (const_string "1")
16666               ]
16667               (const_string "*")))
16668    (set_attr "mode" "<MODE>")])
16669
16670 (define_insn "pro_epilogue_adjust_stack_<mode>_sub"
16671   [(set (match_operand:P 0 "register_operand" "=r")
16672         (minus:P (match_operand:P 1 "register_operand" "0")
16673                  (match_operand:P 2 "register_operand" "r")))
16674    (clobber (reg:CC FLAGS_REG))
16675    (clobber (mem:BLK (scratch)))]
16676   ""
16677   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
16678   [(set_attr "type" "alu")
16679    (set_attr "mode" "<MODE>")])
16680
16681 (define_insn "allocate_stack_worker_probe_<mode>"
16682   [(set (match_operand:P 0 "register_operand" "=a")
16683         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16684                             UNSPECV_STACK_PROBE))
16685    (clobber (reg:CC FLAGS_REG))]
16686   "ix86_target_stack_probe ()"
16687   "call\t___chkstk_ms"
16688   [(set_attr "type" "multi")
16689    (set_attr "length" "5")])
16690
16691 (define_expand "allocate_stack"
16692   [(match_operand 0 "register_operand" "")
16693    (match_operand 1 "general_operand" "")]
16694   "ix86_target_stack_probe ()"
16695 {
16696   rtx x;
16697
16698 #ifndef CHECK_STACK_LIMIT
16699 #define CHECK_STACK_LIMIT 0
16700 #endif
16701
16702   if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
16703       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
16704     {
16705       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
16706                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16707       if (x != stack_pointer_rtx)
16708         emit_move_insn (stack_pointer_rtx, x);
16709     }
16710   else
16711     {
16712       x = copy_to_mode_reg (Pmode, operands[1]);
16713       if (TARGET_64BIT)
16714         emit_insn (gen_allocate_stack_worker_probe_di (x, x));
16715       else
16716         emit_insn (gen_allocate_stack_worker_probe_si (x, x));
16717       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, x,
16718                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16719       if (x != stack_pointer_rtx)
16720         emit_move_insn (stack_pointer_rtx, x);
16721     }
16722
16723   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
16724   DONE;
16725 })
16726
16727 ;; Use IOR for stack probes, this is shorter.
16728 (define_expand "probe_stack"
16729   [(match_operand 0 "memory_operand" "")]
16730   ""
16731 {
16732   rtx (*gen_ior3) (rtx, rtx, rtx);
16733
16734   gen_ior3 = (GET_MODE (operands[0]) == DImode
16735               ? gen_iordi3 : gen_iorsi3);
16736
16737   emit_insn (gen_ior3 (operands[0], operands[0], const0_rtx));
16738   DONE;
16739 })
16740
16741 (define_insn "adjust_stack_and_probe<mode>"
16742   [(set (match_operand:P 0 "register_operand" "=r")
16743         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16744                             UNSPECV_PROBE_STACK_RANGE))
16745    (set (reg:P SP_REG)
16746         (minus:P (reg:P SP_REG) (match_operand:P 2 "const_int_operand" "n")))
16747    (clobber (reg:CC FLAGS_REG))
16748    (clobber (mem:BLK (scratch)))]
16749   ""
16750   "* return output_adjust_stack_and_probe (operands[0]);"
16751   [(set_attr "type" "multi")])
16752
16753 (define_insn "probe_stack_range<mode>"
16754   [(set (match_operand:P 0 "register_operand" "=r")
16755         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")
16756                             (match_operand:P 2 "const_int_operand" "n")]
16757                             UNSPECV_PROBE_STACK_RANGE))
16758    (clobber (reg:CC FLAGS_REG))]
16759   ""
16760   "* return output_probe_stack_range (operands[0], operands[2]);"
16761   [(set_attr "type" "multi")])
16762
16763 (define_expand "builtin_setjmp_receiver"
16764   [(label_ref (match_operand 0 "" ""))]
16765   "!TARGET_64BIT && flag_pic"
16766 {
16767 #if TARGET_MACHO
16768   if (TARGET_MACHO)
16769     {
16770       rtx xops[3];
16771       rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
16772       rtx label_rtx = gen_label_rtx ();
16773       emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
16774       xops[0] = xops[1] = picreg;
16775       xops[2] = machopic_gen_offset (gen_rtx_LABEL_REF (SImode, label_rtx));
16776       ix86_expand_binary_operator (MINUS, SImode, xops);
16777     }
16778   else
16779 #endif
16780     emit_insn (gen_set_got (pic_offset_table_rtx));
16781   DONE;
16782 })
16783 \f
16784 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
16785
16786 (define_split
16787   [(set (match_operand 0 "register_operand" "")
16788         (match_operator 3 "promotable_binary_operator"
16789            [(match_operand 1 "register_operand" "")
16790             (match_operand 2 "aligned_operand" "")]))
16791    (clobber (reg:CC FLAGS_REG))]
16792   "! TARGET_PARTIAL_REG_STALL && reload_completed
16793    && ((GET_MODE (operands[0]) == HImode
16794         && ((optimize_function_for_speed_p (cfun) && !TARGET_FAST_PREFIX)
16795             /* ??? next two lines just !satisfies_constraint_K (...) */
16796             || !CONST_INT_P (operands[2])
16797             || satisfies_constraint_K (operands[2])))
16798        || (GET_MODE (operands[0]) == QImode
16799            && (TARGET_PROMOTE_QImode || optimize_function_for_size_p (cfun))))"
16800   [(parallel [(set (match_dup 0)
16801                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
16802               (clobber (reg:CC FLAGS_REG))])]
16803 {
16804   operands[0] = gen_lowpart (SImode, operands[0]);
16805   operands[1] = gen_lowpart (SImode, operands[1]);
16806   if (GET_CODE (operands[3]) != ASHIFT)
16807     operands[2] = gen_lowpart (SImode, operands[2]);
16808   PUT_MODE (operands[3], SImode);
16809 })
16810
16811 ; Promote the QImode tests, as i386 has encoding of the AND
16812 ; instruction with 32-bit sign-extended immediate and thus the
16813 ; instruction size is unchanged, except in the %eax case for
16814 ; which it is increased by one byte, hence the ! optimize_size.
16815 (define_split
16816   [(set (match_operand 0 "flags_reg_operand" "")
16817         (match_operator 2 "compare_operator"
16818           [(and (match_operand 3 "aligned_operand" "")
16819                 (match_operand 4 "const_int_operand" ""))
16820            (const_int 0)]))
16821    (set (match_operand 1 "register_operand" "")
16822         (and (match_dup 3) (match_dup 4)))]
16823   "! TARGET_PARTIAL_REG_STALL && reload_completed
16824    && optimize_insn_for_speed_p ()
16825    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
16826        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
16827    /* Ensure that the operand will remain sign-extended immediate.  */
16828    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
16829   [(parallel [(set (match_dup 0)
16830                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
16831                                     (const_int 0)]))
16832               (set (match_dup 1)
16833                    (and:SI (match_dup 3) (match_dup 4)))])]
16834 {
16835   operands[4]
16836     = gen_int_mode (INTVAL (operands[4])
16837                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
16838   operands[1] = gen_lowpart (SImode, operands[1]);
16839   operands[3] = gen_lowpart (SImode, operands[3]);
16840 })
16841
16842 ; Don't promote the QImode tests, as i386 doesn't have encoding of
16843 ; the TEST instruction with 32-bit sign-extended immediate and thus
16844 ; the instruction size would at least double, which is not what we
16845 ; want even with ! optimize_size.
16846 (define_split
16847   [(set (match_operand 0 "flags_reg_operand" "")
16848         (match_operator 1 "compare_operator"
16849           [(and (match_operand:HI 2 "aligned_operand" "")
16850                 (match_operand:HI 3 "const_int_operand" ""))
16851            (const_int 0)]))]
16852   "! TARGET_PARTIAL_REG_STALL && reload_completed
16853    && ! TARGET_FAST_PREFIX
16854    && optimize_insn_for_speed_p ()
16855    /* Ensure that the operand will remain sign-extended immediate.  */
16856    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
16857   [(set (match_dup 0)
16858         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
16859                          (const_int 0)]))]
16860 {
16861   operands[3]
16862     = gen_int_mode (INTVAL (operands[3])
16863                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
16864   operands[2] = gen_lowpart (SImode, operands[2]);
16865 })
16866
16867 (define_split
16868   [(set (match_operand 0 "register_operand" "")
16869         (neg (match_operand 1 "register_operand" "")))
16870    (clobber (reg:CC FLAGS_REG))]
16871   "! TARGET_PARTIAL_REG_STALL && reload_completed
16872    && (GET_MODE (operands[0]) == HImode
16873        || (GET_MODE (operands[0]) == QImode
16874            && (TARGET_PROMOTE_QImode
16875                || optimize_insn_for_size_p ())))"
16876   [(parallel [(set (match_dup 0)
16877                    (neg:SI (match_dup 1)))
16878               (clobber (reg:CC FLAGS_REG))])]
16879 {
16880   operands[0] = gen_lowpart (SImode, operands[0]);
16881   operands[1] = gen_lowpart (SImode, operands[1]);
16882 })
16883
16884 (define_split
16885   [(set (match_operand 0 "register_operand" "")
16886         (not (match_operand 1 "register_operand" "")))]
16887   "! TARGET_PARTIAL_REG_STALL && reload_completed
16888    && (GET_MODE (operands[0]) == HImode
16889        || (GET_MODE (operands[0]) == QImode
16890            && (TARGET_PROMOTE_QImode
16891                || optimize_insn_for_size_p ())))"
16892   [(set (match_dup 0)
16893         (not:SI (match_dup 1)))]
16894 {
16895   operands[0] = gen_lowpart (SImode, operands[0]);
16896   operands[1] = gen_lowpart (SImode, operands[1]);
16897 })
16898 \f
16899 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
16900 ;; transform a complex memory operation into two memory to register operations.
16901
16902 ;; Don't push memory operands
16903 (define_peephole2
16904   [(set (match_operand:SWI 0 "push_operand" "")
16905         (match_operand:SWI 1 "memory_operand" ""))
16906    (match_scratch:SWI 2 "<r>")]
16907   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16908    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16909   [(set (match_dup 2) (match_dup 1))
16910    (set (match_dup 0) (match_dup 2))])
16911
16912 ;; We need to handle SFmode only, because DFmode and XFmode are split to
16913 ;; SImode pushes.
16914 (define_peephole2
16915   [(set (match_operand:SF 0 "push_operand" "")
16916         (match_operand:SF 1 "memory_operand" ""))
16917    (match_scratch:SF 2 "r")]
16918   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16919    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16920   [(set (match_dup 2) (match_dup 1))
16921    (set (match_dup 0) (match_dup 2))])
16922
16923 ;; Don't move an immediate directly to memory when the instruction
16924 ;; gets too big.
16925 (define_peephole2
16926   [(match_scratch:SWI124 1 "<r>")
16927    (set (match_operand:SWI124 0 "memory_operand" "")
16928         (const_int 0))]
16929   "optimize_insn_for_speed_p ()
16930    && !TARGET_USE_MOV0
16931    && TARGET_SPLIT_LONG_MOVES
16932    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
16933    && peep2_regno_dead_p (0, FLAGS_REG)"
16934   [(parallel [(set (match_dup 2) (const_int 0))
16935               (clobber (reg:CC FLAGS_REG))])
16936    (set (match_dup 0) (match_dup 1))]
16937   "operands[2] = gen_lowpart (SImode, operands[1]);")
16938
16939 (define_peephole2
16940   [(match_scratch:SWI124 2 "<r>")
16941    (set (match_operand:SWI124 0 "memory_operand" "")
16942         (match_operand:SWI124 1 "immediate_operand" ""))]
16943   "optimize_insn_for_speed_p ()
16944    && TARGET_SPLIT_LONG_MOVES
16945    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
16946   [(set (match_dup 2) (match_dup 1))
16947    (set (match_dup 0) (match_dup 2))])
16948
16949 ;; Don't compare memory with zero, load and use a test instead.
16950 (define_peephole2
16951   [(set (match_operand 0 "flags_reg_operand" "")
16952         (match_operator 1 "compare_operator"
16953           [(match_operand:SI 2 "memory_operand" "")
16954            (const_int 0)]))
16955    (match_scratch:SI 3 "r")]
16956   "optimize_insn_for_speed_p () && ix86_match_ccmode (insn, CCNOmode)"
16957   [(set (match_dup 3) (match_dup 2))
16958    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))])
16959
16960 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
16961 ;; Don't split NOTs with a displacement operand, because resulting XOR
16962 ;; will not be pairable anyway.
16963 ;;
16964 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
16965 ;; represented using a modRM byte.  The XOR replacement is long decoded,
16966 ;; so this split helps here as well.
16967 ;;
16968 ;; Note: Can't do this as a regular split because we can't get proper
16969 ;; lifetime information then.
16970
16971 (define_peephole2
16972   [(set (match_operand:SWI124 0 "nonimmediate_operand" "")
16973         (not:SWI124 (match_operand:SWI124 1 "nonimmediate_operand" "")))]
16974   "optimize_insn_for_speed_p ()
16975    && ((TARGET_NOT_UNPAIRABLE
16976         && (!MEM_P (operands[0])
16977             || !memory_displacement_operand (operands[0], <MODE>mode)))
16978        || (TARGET_NOT_VECTORMODE
16979            && long_memory_operand (operands[0], <MODE>mode)))
16980    && peep2_regno_dead_p (0, FLAGS_REG)"
16981   [(parallel [(set (match_dup 0)
16982                    (xor:SWI124 (match_dup 1) (const_int -1)))
16983               (clobber (reg:CC FLAGS_REG))])])
16984
16985 ;; Non pairable "test imm, reg" instructions can be translated to
16986 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
16987 ;; byte opcode instead of two, have a short form for byte operands),
16988 ;; so do it for other CPUs as well.  Given that the value was dead,
16989 ;; this should not create any new dependencies.  Pass on the sub-word
16990 ;; versions if we're concerned about partial register stalls.
16991
16992 (define_peephole2
16993   [(set (match_operand 0 "flags_reg_operand" "")
16994         (match_operator 1 "compare_operator"
16995           [(and:SI (match_operand:SI 2 "register_operand" "")
16996                    (match_operand:SI 3 "immediate_operand" ""))
16997            (const_int 0)]))]
16998   "ix86_match_ccmode (insn, CCNOmode)
16999    && (true_regnum (operands[2]) != AX_REG
17000        || satisfies_constraint_K (operands[3]))
17001    && peep2_reg_dead_p (1, operands[2])"
17002   [(parallel
17003      [(set (match_dup 0)
17004            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
17005                             (const_int 0)]))
17006       (set (match_dup 2)
17007            (and:SI (match_dup 2) (match_dup 3)))])])
17008
17009 ;; We don't need to handle HImode case, because it will be promoted to SImode
17010 ;; on ! TARGET_PARTIAL_REG_STALL
17011
17012 (define_peephole2
17013   [(set (match_operand 0 "flags_reg_operand" "")
17014         (match_operator 1 "compare_operator"
17015           [(and:QI (match_operand:QI 2 "register_operand" "")
17016                    (match_operand:QI 3 "immediate_operand" ""))
17017            (const_int 0)]))]
17018   "! TARGET_PARTIAL_REG_STALL
17019    && ix86_match_ccmode (insn, CCNOmode)
17020    && true_regnum (operands[2]) != AX_REG
17021    && peep2_reg_dead_p (1, operands[2])"
17022   [(parallel
17023      [(set (match_dup 0)
17024            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
17025                             (const_int 0)]))
17026       (set (match_dup 2)
17027            (and:QI (match_dup 2) (match_dup 3)))])])
17028
17029 (define_peephole2
17030   [(set (match_operand 0 "flags_reg_operand" "")
17031         (match_operator 1 "compare_operator"
17032           [(and:SI
17033              (zero_extract:SI
17034                (match_operand 2 "ext_register_operand" "")
17035                (const_int 8)
17036                (const_int 8))
17037              (match_operand 3 "const_int_operand" ""))
17038            (const_int 0)]))]
17039   "! TARGET_PARTIAL_REG_STALL
17040    && ix86_match_ccmode (insn, CCNOmode)
17041    && true_regnum (operands[2]) != AX_REG
17042    && peep2_reg_dead_p (1, operands[2])"
17043   [(parallel [(set (match_dup 0)
17044                    (match_op_dup 1
17045                      [(and:SI
17046                         (zero_extract:SI
17047                           (match_dup 2)
17048                           (const_int 8)
17049                           (const_int 8))
17050                         (match_dup 3))
17051                       (const_int 0)]))
17052               (set (zero_extract:SI (match_dup 2)
17053                                     (const_int 8)
17054                                     (const_int 8))
17055                    (and:SI
17056                      (zero_extract:SI
17057                        (match_dup 2)
17058                        (const_int 8)
17059                        (const_int 8))
17060                      (match_dup 3)))])])
17061
17062 ;; Don't do logical operations with memory inputs.
17063 (define_peephole2
17064   [(match_scratch:SI 2 "r")
17065    (parallel [(set (match_operand:SI 0 "register_operand" "")
17066                    (match_operator:SI 3 "arith_or_logical_operator"
17067                      [(match_dup 0)
17068                       (match_operand:SI 1 "memory_operand" "")]))
17069               (clobber (reg:CC FLAGS_REG))])]
17070   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17071   [(set (match_dup 2) (match_dup 1))
17072    (parallel [(set (match_dup 0)
17073                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
17074               (clobber (reg:CC FLAGS_REG))])])
17075
17076 (define_peephole2
17077   [(match_scratch:SI 2 "r")
17078    (parallel [(set (match_operand:SI 0 "register_operand" "")
17079                    (match_operator:SI 3 "arith_or_logical_operator"
17080                      [(match_operand:SI 1 "memory_operand" "")
17081                       (match_dup 0)]))
17082               (clobber (reg:CC FLAGS_REG))])]
17083   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17084   [(set (match_dup 2) (match_dup 1))
17085    (parallel [(set (match_dup 0)
17086                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
17087               (clobber (reg:CC FLAGS_REG))])])
17088
17089 ;; Prefer Load+RegOp to Mov+MemOp.  Watch out for cases when the memory address
17090 ;; refers to the destination of the load!
17091
17092 (define_peephole2
17093   [(set (match_operand:SI 0 "register_operand" "")
17094         (match_operand:SI 1 "register_operand" ""))
17095    (parallel [(set (match_dup 0)
17096                    (match_operator:SI 3 "commutative_operator"
17097                      [(match_dup 0)
17098                       (match_operand:SI 2 "memory_operand" "")]))
17099               (clobber (reg:CC FLAGS_REG))])]
17100   "REGNO (operands[0]) != REGNO (operands[1])
17101    && GENERAL_REGNO_P (REGNO (operands[0]))
17102    && GENERAL_REGNO_P (REGNO (operands[1]))"
17103   [(set (match_dup 0) (match_dup 4))
17104    (parallel [(set (match_dup 0)
17105                    (match_op_dup 3 [(match_dup 0) (match_dup 1)]))
17106               (clobber (reg:CC FLAGS_REG))])]
17107   "operands[4] = replace_rtx (operands[2], operands[0], operands[1]);")
17108
17109 (define_peephole2
17110   [(set (match_operand 0 "register_operand" "")
17111         (match_operand 1 "register_operand" ""))
17112    (set (match_dup 0)
17113                    (match_operator 3 "commutative_operator"
17114                      [(match_dup 0)
17115                       (match_operand 2 "memory_operand" "")]))]
17116   "REGNO (operands[0]) != REGNO (operands[1])
17117    && ((MMX_REG_P (operands[0]) && MMX_REG_P (operands[1])) 
17118        || (SSE_REG_P (operands[0]) && SSE_REG_P (operands[1])))"
17119   [(set (match_dup 0) (match_dup 2))
17120    (set (match_dup 0)
17121         (match_op_dup 3 [(match_dup 0) (match_dup 1)]))])
17122
17123 ; Don't do logical operations with memory outputs
17124 ;
17125 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
17126 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
17127 ; the same decoder scheduling characteristics as the original.
17128
17129 (define_peephole2
17130   [(match_scratch:SI 2 "r")
17131    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17132                    (match_operator:SI 3 "arith_or_logical_operator"
17133                      [(match_dup 0)
17134                       (match_operand:SI 1 "nonmemory_operand" "")]))
17135               (clobber (reg:CC FLAGS_REG))])]
17136   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17137    /* Do not split stack checking probes.  */
17138    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17139   [(set (match_dup 2) (match_dup 0))
17140    (parallel [(set (match_dup 2)
17141                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
17142               (clobber (reg:CC FLAGS_REG))])
17143    (set (match_dup 0) (match_dup 2))])
17144
17145 (define_peephole2
17146   [(match_scratch:SI 2 "r")
17147    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17148                    (match_operator:SI 3 "arith_or_logical_operator"
17149                      [(match_operand:SI 1 "nonmemory_operand" "")
17150                       (match_dup 0)]))
17151               (clobber (reg:CC FLAGS_REG))])]
17152   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17153    /* Do not split stack checking probes.  */
17154    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17155   [(set (match_dup 2) (match_dup 0))
17156    (parallel [(set (match_dup 2)
17157                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
17158               (clobber (reg:CC FLAGS_REG))])
17159    (set (match_dup 0) (match_dup 2))])
17160
17161 ;; Attempt to use arith or logical operations with memory outputs with
17162 ;; setting of flags.
17163 (define_peephole2
17164   [(set (match_operand:SWI 0 "register_operand" "")
17165         (match_operand:SWI 1 "memory_operand" ""))
17166    (parallel [(set (match_dup 0)
17167                    (match_operator:SWI 3 "plusminuslogic_operator"
17168                      [(match_dup 0)
17169                       (match_operand:SWI 2 "<nonmemory_operand>" "")]))
17170               (clobber (reg:CC FLAGS_REG))])
17171    (set (match_dup 1) (match_dup 0))
17172    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17173   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17174    && peep2_reg_dead_p (4, operands[0])
17175    && !reg_overlap_mentioned_p (operands[0], operands[1])
17176    && (<MODE>mode != QImode
17177        || immediate_operand (operands[2], QImode)
17178        || q_regs_operand (operands[2], QImode))
17179    && ix86_match_ccmode (peep2_next_insn (3),
17180                          (GET_CODE (operands[3]) == PLUS
17181                           || GET_CODE (operands[3]) == MINUS)
17182                          ? CCGOCmode : CCNOmode)"
17183   [(parallel [(set (match_dup 4) (match_dup 5))
17184               (set (match_dup 1) (match_op_dup 3 [(match_dup 1)
17185                                                   (match_dup 2)]))])]
17186 {
17187   operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17188   operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17189                                 copy_rtx (operands[1]),
17190                                 copy_rtx (operands[2]));
17191   operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17192                                  operands[5], const0_rtx);
17193 })
17194
17195 (define_peephole2
17196   [(parallel [(set (match_operand:SWI 0 "register_operand" "")
17197                    (match_operator:SWI 2 "plusminuslogic_operator"
17198                      [(match_dup 0)
17199                       (match_operand:SWI 1 "memory_operand" "")]))
17200               (clobber (reg:CC FLAGS_REG))])
17201    (set (match_dup 1) (match_dup 0))
17202    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17203   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17204    && GET_CODE (operands[2]) != MINUS
17205    && peep2_reg_dead_p (3, operands[0])
17206    && !reg_overlap_mentioned_p (operands[0], operands[1])
17207    && ix86_match_ccmode (peep2_next_insn (2),
17208                          GET_CODE (operands[2]) == PLUS
17209                          ? CCGOCmode : CCNOmode)"
17210   [(parallel [(set (match_dup 3) (match_dup 4))
17211               (set (match_dup 1) (match_op_dup 2 [(match_dup 1)
17212                                                   (match_dup 0)]))])]
17213 {
17214   operands[3] = SET_DEST (PATTERN (peep2_next_insn (2)));
17215   operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), <MODE>mode,
17216                                 copy_rtx (operands[1]),
17217                                 copy_rtx (operands[0]));
17218   operands[4] = gen_rtx_COMPARE (GET_MODE (operands[3]),
17219                                  operands[4], const0_rtx);
17220 })
17221
17222 (define_peephole2
17223   [(set (match_operand:SWI12 0 "register_operand" "")
17224         (match_operand:SWI12 1 "memory_operand" ""))
17225    (parallel [(set (match_operand:SI 4 "register_operand" "")
17226                    (match_operator:SI 3 "plusminuslogic_operator"
17227                      [(match_dup 4)
17228                       (match_operand:SI 2 "nonmemory_operand" "")]))
17229               (clobber (reg:CC FLAGS_REG))])
17230    (set (match_dup 1) (match_dup 0))
17231    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17232   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17233    && REG_P (operands[0]) && REG_P (operands[4])
17234    && REGNO (operands[0]) == REGNO (operands[4])
17235    && peep2_reg_dead_p (4, operands[0])
17236    && (<MODE>mode != QImode
17237        || immediate_operand (operands[2], SImode)
17238        || q_regs_operand (operands[2], SImode))
17239    && !reg_overlap_mentioned_p (operands[0], operands[1])
17240    && ix86_match_ccmode (peep2_next_insn (3),
17241                          (GET_CODE (operands[3]) == PLUS
17242                           || GET_CODE (operands[3]) == MINUS)
17243                          ? CCGOCmode : CCNOmode)"
17244   [(parallel [(set (match_dup 4) (match_dup 5))
17245               (set (match_dup 1) (match_dup 6))])]
17246 {
17247   operands[2] = gen_lowpart (<MODE>mode, operands[2]);
17248   operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17249   operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17250                                 copy_rtx (operands[1]), operands[2]);
17251   operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17252                                  operands[5], const0_rtx);
17253   operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17254                                 copy_rtx (operands[1]),
17255                                 copy_rtx (operands[2]));
17256 })
17257
17258 ;; Attempt to always use XOR for zeroing registers.
17259 (define_peephole2
17260   [(set (match_operand 0 "register_operand" "")
17261         (match_operand 1 "const0_operand" ""))]
17262   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
17263    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17264    && GENERAL_REG_P (operands[0])
17265    && peep2_regno_dead_p (0, FLAGS_REG)"
17266   [(parallel [(set (match_dup 0) (const_int 0))
17267               (clobber (reg:CC FLAGS_REG))])]
17268   "operands[0] = gen_lowpart (word_mode, operands[0]);")
17269
17270 (define_peephole2
17271   [(set (strict_low_part (match_operand 0 "register_operand" ""))
17272         (const_int 0))]
17273   "(GET_MODE (operands[0]) == QImode
17274     || GET_MODE (operands[0]) == HImode)
17275    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17276    && peep2_regno_dead_p (0, FLAGS_REG)"
17277   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
17278               (clobber (reg:CC FLAGS_REG))])])
17279
17280 ;; For HI, SI and DI modes, or $-1,reg is smaller than mov $-1,reg.
17281 (define_peephole2
17282   [(set (match_operand:SWI248 0 "register_operand" "")
17283         (const_int -1))]
17284   "(optimize_insn_for_size_p () || TARGET_MOVE_M1_VIA_OR)
17285    && peep2_regno_dead_p (0, FLAGS_REG)"
17286   [(parallel [(set (match_dup 0) (const_int -1))
17287               (clobber (reg:CC FLAGS_REG))])]
17288 {
17289   if (GET_MODE_SIZE (<MODE>mode) < GET_MODE_SIZE (SImode))
17290     operands[0] = gen_lowpart (SImode, operands[0]);
17291 })
17292
17293 ;; Attempt to convert simple lea to add/shift.
17294 ;; These can be created by move expanders.
17295
17296 (define_peephole2
17297   [(set (match_operand:SWI48 0 "register_operand" "")
17298         (plus:SWI48 (match_dup 0)
17299                     (match_operand:SWI48 1 "<nonmemory_operand>" "")))]
17300   "peep2_regno_dead_p (0, FLAGS_REG)"
17301   [(parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (match_dup 1)))
17302               (clobber (reg:CC FLAGS_REG))])])
17303
17304 (define_peephole2
17305   [(set (match_operand:SI 0 "register_operand" "")
17306         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
17307                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
17308   "TARGET_64BIT
17309    && peep2_regno_dead_p (0, FLAGS_REG)
17310    && REGNO (operands[0]) == REGNO (operands[1])"
17311   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
17312               (clobber (reg:CC FLAGS_REG))])]
17313   "operands[2] = gen_lowpart (SImode, operands[2]);")
17314
17315 (define_peephole2
17316   [(set (match_operand:SWI48 0 "register_operand" "")
17317         (mult:SWI48 (match_dup 0)
17318                     (match_operand:SWI48 1 "const_int_operand" "")))]
17319   "exact_log2 (INTVAL (operands[1])) >= 0
17320    && peep2_regno_dead_p (0, FLAGS_REG)"
17321   [(parallel [(set (match_dup 0) (ashift:SWI48 (match_dup 0) (match_dup 2)))
17322               (clobber (reg:CC FLAGS_REG))])]
17323   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
17324
17325 (define_peephole2
17326   [(set (match_operand:SI 0 "register_operand" "")
17327         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
17328                    (match_operand:DI 2 "const_int_operand" "")) 0))]
17329   "TARGET_64BIT
17330    && exact_log2 (INTVAL (operands[2])) >= 0
17331    && REGNO (operands[0]) == REGNO (operands[1])
17332    && peep2_regno_dead_p (0, FLAGS_REG)"
17333   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
17334               (clobber (reg:CC FLAGS_REG))])]
17335   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
17336
17337 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
17338 ;; code is shorter, since push is only 1 byte, while add imm, %esp is 3 bytes.
17339 ;; On many CPUs it is also faster, since special hardware to avoid esp
17340 ;; dependencies is present.
17341
17342 ;; While some of these conversions may be done using splitters, we use
17343 ;; peepholes in order to allow combine_stack_adjustments pass to see
17344 ;; nonobfuscated RTL.
17345
17346 ;; Convert prologue esp subtractions to push.
17347 ;; We need register to push.  In order to keep verify_flow_info happy we have
17348 ;; two choices
17349 ;; - use scratch and clobber it in order to avoid dependencies
17350 ;; - use already live register
17351 ;; We can't use the second way right now, since there is no reliable way how to
17352 ;; verify that given register is live.  First choice will also most likely in
17353 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
17354 ;; call clobbered registers are dead.  We may want to use base pointer as an
17355 ;; alternative when no register is available later.
17356
17357 (define_peephole2
17358   [(match_scratch:P 1 "r")
17359    (parallel [(set (reg:P SP_REG)
17360                    (plus:P (reg:P SP_REG)
17361                            (match_operand:P 0 "const_int_operand" "")))
17362               (clobber (reg:CC FLAGS_REG))
17363               (clobber (mem:BLK (scratch)))])]
17364   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17365    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17366   [(clobber (match_dup 1))
17367    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17368               (clobber (mem:BLK (scratch)))])])
17369
17370 (define_peephole2
17371   [(match_scratch:P 1 "r")
17372    (parallel [(set (reg:P SP_REG)
17373                    (plus:P (reg:P SP_REG)
17374                            (match_operand:P 0 "const_int_operand" "")))
17375               (clobber (reg:CC FLAGS_REG))
17376               (clobber (mem:BLK (scratch)))])]
17377   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17378    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17379   [(clobber (match_dup 1))
17380    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17381    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17382               (clobber (mem:BLK (scratch)))])])
17383
17384 ;; Convert esp subtractions to push.
17385 (define_peephole2
17386   [(match_scratch:P 1 "r")
17387    (parallel [(set (reg:P SP_REG)
17388                    (plus:P (reg:P SP_REG)
17389                            (match_operand:P 0 "const_int_operand" "")))
17390               (clobber (reg:CC FLAGS_REG))])]
17391   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17392    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17393   [(clobber (match_dup 1))
17394    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17395
17396 (define_peephole2
17397   [(match_scratch:P 1 "r")
17398    (parallel [(set (reg:P SP_REG)
17399                    (plus:P (reg:P SP_REG)
17400                            (match_operand:P 0 "const_int_operand" "")))
17401               (clobber (reg:CC FLAGS_REG))])]
17402   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17403    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17404   [(clobber (match_dup 1))
17405    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17406    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17407
17408 ;; Convert epilogue deallocator to pop.
17409 (define_peephole2
17410   [(match_scratch:P 1 "r")
17411    (parallel [(set (reg:P SP_REG)
17412                    (plus:P (reg:P SP_REG)
17413                            (match_operand:P 0 "const_int_operand" "")))
17414               (clobber (reg:CC FLAGS_REG))
17415               (clobber (mem:BLK (scratch)))])]
17416   "(TARGET_SINGLE_POP || optimize_insn_for_size_p ())
17417    && INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17418   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17419               (clobber (mem:BLK (scratch)))])])
17420
17421 ;; Two pops case is tricky, since pop causes dependency
17422 ;; on destination register.  We use two registers if available.
17423 (define_peephole2
17424   [(match_scratch:P 1 "r")
17425    (match_scratch:P 2 "r")
17426    (parallel [(set (reg:P SP_REG)
17427                    (plus:P (reg:P SP_REG)
17428                            (match_operand:P 0 "const_int_operand" "")))
17429               (clobber (reg:CC FLAGS_REG))
17430               (clobber (mem:BLK (scratch)))])]
17431   "(TARGET_DOUBLE_POP || optimize_insn_for_size_p ())
17432    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17433   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17434               (clobber (mem:BLK (scratch)))])
17435    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17436
17437 (define_peephole2
17438   [(match_scratch:P 1 "r")
17439    (parallel [(set (reg:P SP_REG)
17440                    (plus:P (reg:P SP_REG)
17441                            (match_operand:P 0 "const_int_operand" "")))
17442               (clobber (reg:CC FLAGS_REG))
17443               (clobber (mem:BLK (scratch)))])]
17444   "optimize_insn_for_size_p ()
17445    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17446   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17447               (clobber (mem:BLK (scratch)))])
17448    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17449
17450 ;; Convert esp additions to pop.
17451 (define_peephole2
17452   [(match_scratch:P 1 "r")
17453    (parallel [(set (reg:P SP_REG)
17454                    (plus:P (reg:P SP_REG)
17455                            (match_operand:P 0 "const_int_operand" "")))
17456               (clobber (reg:CC FLAGS_REG))])]
17457   "INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17458   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17459
17460 ;; Two pops case is tricky, since pop causes dependency
17461 ;; on destination register.  We use two registers if available.
17462 (define_peephole2
17463   [(match_scratch:P 1 "r")
17464    (match_scratch:P 2 "r")
17465    (parallel [(set (reg:P SP_REG)
17466                    (plus:P (reg:P SP_REG)
17467                            (match_operand:P 0 "const_int_operand" "")))
17468               (clobber (reg:CC FLAGS_REG))])]
17469   "INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17470   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17471    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17472
17473 (define_peephole2
17474   [(match_scratch:P 1 "r")
17475    (parallel [(set (reg:P SP_REG)
17476                    (plus:P (reg:P SP_REG)
17477                            (match_operand:P 0 "const_int_operand" "")))
17478               (clobber (reg:CC FLAGS_REG))])]
17479   "optimize_insn_for_size_p ()
17480    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17481   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17482    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17483 \f
17484 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
17485 ;; required and register dies.  Similarly for 128 to -128.
17486 (define_peephole2
17487   [(set (match_operand 0 "flags_reg_operand" "")
17488         (match_operator 1 "compare_operator"
17489           [(match_operand 2 "register_operand" "")
17490            (match_operand 3 "const_int_operand" "")]))]
17491   "(((!TARGET_FUSE_CMP_AND_BRANCH || optimize_insn_for_size_p ())
17492      && incdec_operand (operands[3], GET_MODE (operands[3])))
17493     || (!TARGET_FUSE_CMP_AND_BRANCH
17494         && INTVAL (operands[3]) == 128))
17495    && ix86_match_ccmode (insn, CCGCmode)
17496    && peep2_reg_dead_p (1, operands[2])"
17497   [(parallel [(set (match_dup 0)
17498                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
17499               (clobber (match_dup 2))])])
17500 \f
17501 ;; Convert imul by three, five and nine into lea
17502 (define_peephole2
17503   [(parallel
17504     [(set (match_operand:SWI48 0 "register_operand" "")
17505           (mult:SWI48 (match_operand:SWI48 1 "register_operand" "")
17506                       (match_operand:SWI48 2 "const359_operand" "")))
17507      (clobber (reg:CC FLAGS_REG))])]
17508   "!TARGET_PARTIAL_REG_STALL
17509    || <MODE>mode == SImode
17510    || optimize_function_for_size_p (cfun)"
17511   [(set (match_dup 0)
17512         (plus:SWI48 (mult:SWI48 (match_dup 1) (match_dup 2))
17513                     (match_dup 1)))]
17514   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17515
17516 (define_peephole2
17517   [(parallel
17518     [(set (match_operand:SWI48 0 "register_operand" "")
17519           (mult:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
17520                       (match_operand:SWI48 2 "const359_operand" "")))
17521      (clobber (reg:CC FLAGS_REG))])]
17522   "optimize_insn_for_speed_p ()
17523    && (!TARGET_PARTIAL_REG_STALL || <MODE>mode == SImode)"
17524   [(set (match_dup 0) (match_dup 1))
17525    (set (match_dup 0)
17526         (plus:SWI48 (mult:SWI48 (match_dup 0) (match_dup 2))
17527                     (match_dup 0)))]
17528   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17529
17530 ;; imul $32bit_imm, mem, reg is vector decoded, while
17531 ;; imul $32bit_imm, reg, reg is direct decoded.
17532 (define_peephole2
17533   [(match_scratch:SWI48 3 "r")
17534    (parallel [(set (match_operand:SWI48 0 "register_operand" "")
17535                    (mult:SWI48 (match_operand:SWI48 1 "memory_operand" "")
17536                                (match_operand:SWI48 2 "immediate_operand" "")))
17537               (clobber (reg:CC FLAGS_REG))])]
17538   "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17539    && !satisfies_constraint_K (operands[2])"
17540   [(set (match_dup 3) (match_dup 1))
17541    (parallel [(set (match_dup 0) (mult:SWI48 (match_dup 3) (match_dup 2)))
17542               (clobber (reg:CC FLAGS_REG))])])
17543
17544 (define_peephole2
17545   [(match_scratch:SI 3 "r")
17546    (parallel [(set (match_operand:DI 0 "register_operand" "")
17547                    (zero_extend:DI
17548                      (mult:SI (match_operand:SI 1 "memory_operand" "")
17549                               (match_operand:SI 2 "immediate_operand" ""))))
17550               (clobber (reg:CC FLAGS_REG))])]
17551   "TARGET_64BIT
17552    && TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17553    && !satisfies_constraint_K (operands[2])"
17554   [(set (match_dup 3) (match_dup 1))
17555    (parallel [(set (match_dup 0)
17556                    (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
17557               (clobber (reg:CC FLAGS_REG))])])
17558
17559 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
17560 ;; Convert it into imul reg, reg
17561 ;; It would be better to force assembler to encode instruction using long
17562 ;; immediate, but there is apparently no way to do so.
17563 (define_peephole2
17564   [(parallel [(set (match_operand:SWI248 0 "register_operand" "")
17565                    (mult:SWI248
17566                     (match_operand:SWI248 1 "nonimmediate_operand" "")
17567                     (match_operand:SWI248 2 "const_int_operand" "")))
17568               (clobber (reg:CC FLAGS_REG))])
17569    (match_scratch:SWI248 3 "r")]
17570   "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()
17571    && satisfies_constraint_K (operands[2])"
17572   [(set (match_dup 3) (match_dup 2))
17573    (parallel [(set (match_dup 0) (mult:SWI248 (match_dup 0) (match_dup 3)))
17574               (clobber (reg:CC FLAGS_REG))])]
17575 {
17576   if (!rtx_equal_p (operands[0], operands[1]))
17577     emit_move_insn (operands[0], operands[1]);
17578 })
17579
17580 ;; After splitting up read-modify operations, array accesses with memory
17581 ;; operands might end up in form:
17582 ;;  sall    $2, %eax
17583 ;;  movl    4(%esp), %edx
17584 ;;  addl    %edx, %eax
17585 ;; instead of pre-splitting:
17586 ;;  sall    $2, %eax
17587 ;;  addl    4(%esp), %eax
17588 ;; Turn it into:
17589 ;;  movl    4(%esp), %edx
17590 ;;  leal    (%edx,%eax,4), %eax
17591
17592 (define_peephole2
17593   [(match_scratch:P 5 "r")
17594    (parallel [(set (match_operand 0 "register_operand" "")
17595                    (ashift (match_operand 1 "register_operand" "")
17596                            (match_operand 2 "const_int_operand" "")))
17597                (clobber (reg:CC FLAGS_REG))])
17598    (parallel [(set (match_operand 3 "register_operand" "")
17599                    (plus (match_dup 0)
17600                          (match_operand 4 "x86_64_general_operand" "")))
17601                    (clobber (reg:CC FLAGS_REG))])]
17602   "IN_RANGE (INTVAL (operands[2]), 1, 3)
17603    /* Validate MODE for lea.  */
17604    && ((!TARGET_PARTIAL_REG_STALL
17605         && (GET_MODE (operands[0]) == QImode
17606             || GET_MODE (operands[0]) == HImode))
17607        || GET_MODE (operands[0]) == SImode
17608        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
17609    && (rtx_equal_p (operands[0], operands[3])
17610        || peep2_reg_dead_p (2, operands[0]))
17611    /* We reorder load and the shift.  */
17612    && !reg_overlap_mentioned_p (operands[0], operands[4])"
17613   [(set (match_dup 5) (match_dup 4))
17614    (set (match_dup 0) (match_dup 1))]
17615 {
17616   enum machine_mode op1mode = GET_MODE (operands[1]);
17617   enum machine_mode mode = op1mode == DImode ? DImode : SImode;
17618   int scale = 1 << INTVAL (operands[2]);
17619   rtx index = gen_lowpart (Pmode, operands[1]);
17620   rtx base = gen_lowpart (Pmode, operands[5]);
17621   rtx dest = gen_lowpart (mode, operands[3]);
17622
17623   operands[1] = gen_rtx_PLUS (Pmode, base,
17624                               gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
17625   operands[5] = base;
17626   if (mode != Pmode)
17627     operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
17628   if (op1mode != Pmode)
17629     operands[5] = gen_rtx_SUBREG (op1mode, operands[5], 0);
17630   operands[0] = dest;
17631 })
17632 \f
17633 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
17634 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
17635 ;; caught for use by garbage collectors and the like.  Using an insn that
17636 ;; maps to SIGILL makes it more likely the program will rightfully die.
17637 ;; Keeping with tradition, "6" is in honor of #UD.
17638 (define_insn "trap"
17639   [(trap_if (const_int 1) (const_int 6))]
17640   ""
17641   { return ASM_SHORT "0x0b0f"; }
17642   [(set_attr "length" "2")])
17643
17644 (define_expand "prefetch"
17645   [(prefetch (match_operand 0 "address_operand" "")
17646              (match_operand:SI 1 "const_int_operand" "")
17647              (match_operand:SI 2 "const_int_operand" ""))]
17648   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
17649 {
17650   int rw = INTVAL (operands[1]);
17651   int locality = INTVAL (operands[2]);
17652
17653   gcc_assert (rw == 0 || rw == 1);
17654   gcc_assert (locality >= 0 && locality <= 3);
17655   gcc_assert (GET_MODE (operands[0]) == Pmode
17656               || GET_MODE (operands[0]) == VOIDmode);
17657
17658   /* Use 3dNOW prefetch in case we are asking for write prefetch not
17659      supported by SSE counterpart or the SSE prefetch is not available
17660      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
17661      of locality.  */
17662   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
17663     operands[2] = GEN_INT (3);
17664   else
17665     operands[1] = const0_rtx;
17666 })
17667
17668 (define_insn "*prefetch_sse_<mode>"
17669   [(prefetch (match_operand:P 0 "address_operand" "p")
17670              (const_int 0)
17671              (match_operand:SI 1 "const_int_operand" ""))]
17672   "TARGET_PREFETCH_SSE"
17673 {
17674   static const char * const patterns[4] = {
17675    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
17676   };
17677
17678   int locality = INTVAL (operands[1]);
17679   gcc_assert (locality >= 0 && locality <= 3);
17680
17681   return patterns[locality];
17682 }
17683   [(set_attr "type" "sse")
17684    (set_attr "atom_sse_attr" "prefetch")
17685    (set (attr "length_address")
17686         (symbol_ref "memory_address_length (operands[0])"))
17687    (set_attr "memory" "none")])
17688
17689 (define_insn "*prefetch_3dnow_<mode>"
17690   [(prefetch (match_operand:P 0 "address_operand" "p")
17691              (match_operand:SI 1 "const_int_operand" "n")
17692              (const_int 3))]
17693   "TARGET_3DNOW"
17694 {
17695   if (INTVAL (operands[1]) == 0)
17696     return "prefetch\t%a0";
17697   else
17698     return "prefetchw\t%a0";
17699 }
17700   [(set_attr "type" "mmx")
17701    (set (attr "length_address")
17702         (symbol_ref "memory_address_length (operands[0])"))
17703    (set_attr "memory" "none")])
17704
17705 (define_expand "stack_protect_set"
17706   [(match_operand 0 "memory_operand" "")
17707    (match_operand 1 "memory_operand" "")]
17708   ""
17709 {
17710   rtx (*insn)(rtx, rtx);
17711
17712 #ifdef TARGET_THREAD_SSP_OFFSET
17713   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17714   insn = (TARGET_LP64
17715           ? gen_stack_tls_protect_set_di
17716           : gen_stack_tls_protect_set_si);
17717 #else
17718   insn = (TARGET_LP64
17719           ? gen_stack_protect_set_di
17720           : gen_stack_protect_set_si);
17721 #endif
17722
17723   emit_insn (insn (operands[0], operands[1]));
17724   DONE;
17725 })
17726
17727 (define_insn "stack_protect_set_<mode>"
17728   [(set (match_operand:PTR 0 "memory_operand" "=m")
17729         (unspec:PTR [(match_operand:PTR 1 "memory_operand" "m")]
17730                     UNSPEC_SP_SET))
17731    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17732    (clobber (reg:CC FLAGS_REG))]
17733   ""
17734   "mov{<imodesuffix>}\t{%1, %2|%2, %1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17735   [(set_attr "type" "multi")])
17736
17737 (define_insn "stack_tls_protect_set_<mode>"
17738   [(set (match_operand:PTR 0 "memory_operand" "=m")
17739         (unspec:PTR [(match_operand:PTR 1 "const_int_operand" "i")]
17740                     UNSPEC_SP_TLS_SET))
17741    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17742    (clobber (reg:CC FLAGS_REG))]
17743   ""
17744   "mov{<imodesuffix>}\t{%@:%P1, %2|%2, <iptrsize> PTR %@:%P1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17745   [(set_attr "type" "multi")])
17746
17747 (define_expand "stack_protect_test"
17748   [(match_operand 0 "memory_operand" "")
17749    (match_operand 1 "memory_operand" "")
17750    (match_operand 2 "" "")]
17751   ""
17752 {
17753   rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
17754
17755   rtx (*insn)(rtx, rtx, rtx);
17756
17757 #ifdef TARGET_THREAD_SSP_OFFSET
17758   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17759   insn = (TARGET_LP64
17760           ? gen_stack_tls_protect_test_di
17761           : gen_stack_tls_protect_test_si);
17762 #else
17763   insn = (TARGET_LP64
17764           ? gen_stack_protect_test_di
17765           : gen_stack_protect_test_si);
17766 #endif
17767
17768   emit_insn (insn (flags, operands[0], operands[1]));
17769
17770   emit_jump_insn (gen_cbranchcc4 (gen_rtx_EQ (VOIDmode, flags, const0_rtx),
17771                                   flags, const0_rtx, operands[2]));
17772   DONE;
17773 })
17774
17775 (define_insn "stack_protect_test_<mode>"
17776   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
17777         (unspec:CCZ [(match_operand:PTR 1 "memory_operand" "m")
17778                      (match_operand:PTR 2 "memory_operand" "m")]
17779                     UNSPEC_SP_TEST))
17780    (clobber (match_scratch:PTR 3 "=&r"))]
17781   ""
17782   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%2, %3|%3, %2}"
17783   [(set_attr "type" "multi")])
17784
17785 (define_insn "stack_tls_protect_test_<mode>"
17786   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
17787         (unspec:CCZ [(match_operand:PTR 1 "memory_operand" "m")
17788                      (match_operand:PTR 2 "const_int_operand" "i")]
17789                     UNSPEC_SP_TLS_TEST))
17790    (clobber (match_scratch:PTR 3 "=r"))]
17791   ""
17792   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%@:%P2, %3|%3, <iptrsize> PTR %@:%P2}"
17793   [(set_attr "type" "multi")])
17794
17795 (define_insn "sse4_2_crc32<mode>"
17796   [(set (match_operand:SI 0 "register_operand" "=r")
17797         (unspec:SI
17798           [(match_operand:SI 1 "register_operand" "0")
17799            (match_operand:SWI124 2 "nonimmediate_operand" "<r>m")]
17800           UNSPEC_CRC32))]
17801   "TARGET_SSE4_2 || TARGET_CRC32"
17802   "crc32{<imodesuffix>}\t{%2, %0|%0, %2}"
17803   [(set_attr "type" "sselog1")
17804    (set_attr "prefix_rep" "1")
17805    (set_attr "prefix_extra" "1")
17806    (set (attr "prefix_data16")
17807      (if_then_else (match_operand:HI 2 "" "")
17808        (const_string "1")
17809        (const_string "*")))
17810    (set (attr "prefix_rex")
17811      (if_then_else (match_operand:QI 2 "ext_QIreg_operand" "")
17812        (const_string "1")
17813        (const_string "*")))
17814    (set_attr "mode" "SI")])
17815
17816 (define_insn "sse4_2_crc32di"
17817   [(set (match_operand:DI 0 "register_operand" "=r")
17818         (unspec:DI
17819           [(match_operand:DI 1 "register_operand" "0")
17820            (match_operand:DI 2 "nonimmediate_operand" "rm")]
17821           UNSPEC_CRC32))]
17822   "TARGET_64BIT && (TARGET_SSE4_2 || TARGET_CRC32)"
17823   "crc32{q}\t{%2, %0|%0, %2}"
17824   [(set_attr "type" "sselog1")
17825    (set_attr "prefix_rep" "1")
17826    (set_attr "prefix_extra" "1")
17827    (set_attr "mode" "DI")])
17828
17829 (define_expand "rdpmc"
17830   [(match_operand:DI 0 "register_operand" "")
17831    (match_operand:SI 1 "register_operand" "")]
17832   ""
17833 {
17834   rtx reg = gen_reg_rtx (DImode);
17835   rtx si;
17836
17837   /* Force operand 1 into ECX.  */
17838   rtx ecx = gen_rtx_REG (SImode, CX_REG);
17839   emit_insn (gen_rtx_SET (VOIDmode, ecx, operands[1]));
17840   si = gen_rtx_UNSPEC_VOLATILE (DImode, gen_rtvec (1, ecx),
17841                                 UNSPECV_RDPMC);
17842
17843   if (TARGET_64BIT)
17844     {
17845       rtvec vec = rtvec_alloc (2);
17846       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17847       rtx upper = gen_reg_rtx (DImode);
17848       rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17849                                         gen_rtvec (1, const0_rtx),
17850                                         UNSPECV_RDPMC);
17851       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, si);
17852       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17853       emit_insn (load);
17854       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17855                                    NULL, 1, OPTAB_DIRECT);
17856       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17857                                  OPTAB_DIRECT);
17858     }
17859   else
17860     emit_insn (gen_rtx_SET (VOIDmode, reg, si));
17861   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17862   DONE;
17863 })
17864
17865 (define_insn "*rdpmc"
17866   [(set (match_operand:DI 0 "register_operand" "=A")
17867         (unspec_volatile:DI [(match_operand:SI 1 "register_operand" "c")]
17868                             UNSPECV_RDPMC))]
17869   "!TARGET_64BIT"
17870   "rdpmc"
17871   [(set_attr "type" "other")
17872    (set_attr "length" "2")])
17873
17874 (define_insn "*rdpmc_rex64"
17875   [(set (match_operand:DI 0 "register_operand" "=a")
17876         (unspec_volatile:DI [(match_operand:SI 2 "register_operand" "c")]
17877                             UNSPECV_RDPMC))
17878   (set (match_operand:DI 1 "register_operand" "=d")
17879        (unspec_volatile:DI [(const_int 0)] UNSPECV_RDPMC))]
17880   "TARGET_64BIT"
17881   "rdpmc"
17882   [(set_attr "type" "other")
17883    (set_attr "length" "2")])
17884
17885 (define_expand "rdtsc"
17886   [(set (match_operand:DI 0 "register_operand" "")
17887         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17888   ""
17889 {
17890   if (TARGET_64BIT)
17891     {
17892       rtvec vec = rtvec_alloc (2);
17893       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17894       rtx upper = gen_reg_rtx (DImode);
17895       rtx lower = gen_reg_rtx (DImode);
17896       rtx src = gen_rtx_UNSPEC_VOLATILE (DImode,
17897                                          gen_rtvec (1, const0_rtx),
17898                                          UNSPECV_RDTSC);
17899       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, lower, src);
17900       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, src);
17901       emit_insn (load);
17902       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17903                                    NULL, 1, OPTAB_DIRECT);
17904       lower = expand_simple_binop (DImode, IOR, lower, upper, lower, 1,
17905                                    OPTAB_DIRECT);
17906       emit_insn (gen_rtx_SET (VOIDmode, operands[0], lower));
17907       DONE;
17908     }
17909 })
17910
17911 (define_insn "*rdtsc"
17912   [(set (match_operand:DI 0 "register_operand" "=A")
17913         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17914   "!TARGET_64BIT"
17915   "rdtsc"
17916   [(set_attr "type" "other")
17917    (set_attr "length" "2")])
17918
17919 (define_insn "*rdtsc_rex64"
17920   [(set (match_operand:DI 0 "register_operand" "=a")
17921         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))
17922    (set (match_operand:DI 1 "register_operand" "=d")
17923         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17924   "TARGET_64BIT"
17925   "rdtsc"
17926   [(set_attr "type" "other")
17927    (set_attr "length" "2")])
17928
17929 (define_expand "rdtscp"
17930   [(match_operand:DI 0 "register_operand" "")
17931    (match_operand:SI 1 "memory_operand" "")]
17932   ""
17933 {
17934   rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17935                                     gen_rtvec (1, const0_rtx),
17936                                     UNSPECV_RDTSCP);
17937   rtx si = gen_rtx_UNSPEC_VOLATILE (SImode,
17938                                     gen_rtvec (1, const0_rtx),
17939                                     UNSPECV_RDTSCP);
17940   rtx reg = gen_reg_rtx (DImode);
17941   rtx tmp = gen_reg_rtx (SImode);
17942
17943   if (TARGET_64BIT)
17944     {
17945       rtvec vec = rtvec_alloc (3);
17946       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17947       rtx upper = gen_reg_rtx (DImode);
17948       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17949       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17950       RTVEC_ELT (vec, 2) = gen_rtx_SET (VOIDmode, tmp, si);
17951       emit_insn (load);
17952       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17953                                    NULL, 1, OPTAB_DIRECT);
17954       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17955                                  OPTAB_DIRECT);
17956     }
17957   else
17958     {
17959       rtvec vec = rtvec_alloc (2);
17960       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17961       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17962       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, tmp, si);
17963       emit_insn (load);
17964     }
17965   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17966   emit_insn (gen_rtx_SET (VOIDmode, operands[1], tmp));
17967   DONE;
17968 })
17969
17970 (define_insn "*rdtscp"
17971   [(set (match_operand:DI 0 "register_operand" "=A")
17972         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17973    (set (match_operand:SI 1 "register_operand" "=c")
17974         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
17975   "!TARGET_64BIT"
17976   "rdtscp"
17977   [(set_attr "type" "other")
17978    (set_attr "length" "3")])
17979
17980 (define_insn "*rdtscp_rex64"
17981   [(set (match_operand:DI 0 "register_operand" "=a")
17982         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17983    (set (match_operand:DI 1 "register_operand" "=d")
17984         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17985    (set (match_operand:SI 2 "register_operand" "=c")
17986         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
17987   "TARGET_64BIT"
17988   "rdtscp"
17989   [(set_attr "type" "other")
17990    (set_attr "length" "3")])
17991
17992 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
17993 ;;
17994 ;; LWP instructions
17995 ;;
17996 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
17997
17998 (define_expand "lwp_llwpcb"
17999   [(unspec_volatile [(match_operand 0 "register_operand" "r")]
18000                     UNSPECV_LLWP_INTRINSIC)]
18001   "TARGET_LWP")
18002
18003 (define_insn "*lwp_llwpcb<mode>1"
18004   [(unspec_volatile [(match_operand:P 0 "register_operand" "r")]
18005                     UNSPECV_LLWP_INTRINSIC)]
18006   "TARGET_LWP"
18007   "llwpcb\t%0"
18008   [(set_attr "type" "lwp")
18009    (set_attr "mode" "<MODE>")
18010    (set_attr "length" "5")])
18011
18012 (define_expand "lwp_slwpcb"
18013   [(set (match_operand 0 "register_operand" "=r")
18014         (unspec_volatile [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18015   "TARGET_LWP"
18016 {
18017   rtx (*insn)(rtx);
18018
18019   insn = (TARGET_64BIT
18020           ? gen_lwp_slwpcbdi
18021           : gen_lwp_slwpcbsi);
18022
18023   emit_insn (insn (operands[0]));
18024   DONE;
18025 })
18026
18027 (define_insn "lwp_slwpcb<mode>"
18028   [(set (match_operand:P 0 "register_operand" "=r")
18029         (unspec_volatile:P [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18030   "TARGET_LWP"
18031   "slwpcb\t%0"
18032   [(set_attr "type" "lwp")
18033    (set_attr "mode" "<MODE>")
18034    (set_attr "length" "5")])
18035
18036 (define_expand "lwp_lwpval<mode>3"
18037   [(unspec_volatile [(match_operand:SWI48 1 "register_operand" "r")
18038                      (match_operand:SI 2 "nonimmediate_operand" "rm")
18039                      (match_operand:SI 3 "const_int_operand" "i")]
18040                     UNSPECV_LWPVAL_INTRINSIC)]
18041   "TARGET_LWP"
18042   ;; Avoid unused variable warning.
18043   "(void) operands[0];")
18044
18045 (define_insn "*lwp_lwpval<mode>3_1"
18046   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")
18047                      (match_operand:SI 1 "nonimmediate_operand" "rm")
18048                      (match_operand:SI 2 "const_int_operand" "i")]
18049                     UNSPECV_LWPVAL_INTRINSIC)]
18050   "TARGET_LWP"
18051   "lwpval\t{%2, %1, %0|%0, %1, %2}"
18052   [(set_attr "type" "lwp")
18053    (set_attr "mode" "<MODE>")
18054    (set (attr "length")
18055         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18056
18057 (define_expand "lwp_lwpins<mode>3"
18058   [(set (reg:CCC FLAGS_REG)
18059         (unspec_volatile:CCC [(match_operand:SWI48 1 "register_operand" "r")
18060                               (match_operand:SI 2 "nonimmediate_operand" "rm")
18061                               (match_operand:SI 3 "const_int_operand" "i")]
18062                              UNSPECV_LWPINS_INTRINSIC))
18063    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
18064         (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))]
18065   "TARGET_LWP")
18066
18067 (define_insn "*lwp_lwpins<mode>3_1"
18068   [(set (reg:CCC FLAGS_REG)
18069         (unspec_volatile:CCC [(match_operand:SWI48 0 "register_operand" "r")
18070                               (match_operand:SI 1 "nonimmediate_operand" "rm")
18071                               (match_operand:SI 2 "const_int_operand" "i")]
18072                              UNSPECV_LWPINS_INTRINSIC))]
18073   "TARGET_LWP"
18074   "lwpins\t{%2, %1, %0|%0, %1, %2}"
18075   [(set_attr "type" "lwp")
18076    (set_attr "mode" "<MODE>")
18077    (set (attr "length")
18078         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18079
18080 (define_insn "rdfsbase<mode>"
18081   [(set (match_operand:SWI48 0 "register_operand" "=r")
18082         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDFSBASE))]
18083   "TARGET_64BIT && TARGET_FSGSBASE"
18084   "rdfsbase %0"
18085   [(set_attr "type" "other")
18086    (set_attr "prefix_extra" "2")])
18087
18088 (define_insn "rdgsbase<mode>"
18089   [(set (match_operand:SWI48 0 "register_operand" "=r")
18090         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDGSBASE))]
18091   "TARGET_64BIT && TARGET_FSGSBASE"
18092   "rdgsbase %0"
18093   [(set_attr "type" "other")
18094    (set_attr "prefix_extra" "2")])
18095
18096 (define_insn "wrfsbase<mode>"
18097   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18098                     UNSPECV_WRFSBASE)]
18099   "TARGET_64BIT && TARGET_FSGSBASE"
18100   "wrfsbase %0"
18101   [(set_attr "type" "other")
18102    (set_attr "prefix_extra" "2")])
18103
18104 (define_insn "wrgsbase<mode>"
18105   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18106                     UNSPECV_WRGSBASE)]
18107   "TARGET_64BIT && TARGET_FSGSBASE"
18108   "wrgsbase %0"
18109   [(set_attr "type" "other")
18110    (set_attr "prefix_extra" "2")])
18111
18112 (define_insn "rdrand<mode>_1"
18113   [(set (match_operand:SWI248 0 "register_operand" "=r")
18114         (unspec_volatile:SWI248 [(const_int 0)] UNSPECV_RDRAND))
18115    (set (reg:CCC FLAGS_REG)
18116         (unspec_volatile:CCC [(const_int 0)] UNSPECV_RDRAND))]
18117   "TARGET_RDRND"
18118   "rdrand\t%0"
18119   [(set_attr "type" "other")
18120    (set_attr "prefix_extra" "1")])
18121
18122 (define_expand "pause"
18123   [(set (match_dup 0)
18124         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18125   ""
18126 {
18127   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
18128   MEM_VOLATILE_P (operands[0]) = 1;
18129 })
18130
18131 ;; Use "rep; nop", instead of "pause", to support older assemblers.
18132 ;; They have the same encoding.
18133 (define_insn "*pause"
18134   [(set (match_operand:BLK 0 "" "")
18135         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18136   ""
18137   "rep; nop"
18138   [(set_attr "length" "2")
18139    (set_attr "memory" "unknown")])
18140
18141 (include "mmx.md")
18142 (include "sse.md")
18143 (include "sync.md")