OSDN Git Service

Backport from mainline
[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,
632                     bmi2,fma4,fma"
633   (const_string "base"))
634
635 (define_attr "enabled" ""
636   (cond [(eq_attr "isa" "sse2") (symbol_ref "TARGET_SSE2")
637          (eq_attr "isa" "sse2_noavx")
638            (symbol_ref "TARGET_SSE2 && !TARGET_AVX")
639          (eq_attr "isa" "sse3") (symbol_ref "TARGET_SSE3")
640          (eq_attr "isa" "sse4") (symbol_ref "TARGET_SSE4_1")
641          (eq_attr "isa" "sse4_noavx")
642            (symbol_ref "TARGET_SSE4_1 && !TARGET_AVX")
643          (eq_attr "isa" "avx") (symbol_ref "TARGET_AVX")
644          (eq_attr "isa" "noavx") (symbol_ref "!TARGET_AVX")
645          (eq_attr "isa" "bmi2") (symbol_ref "TARGET_BMI2")
646          (eq_attr "isa" "fma4") (symbol_ref "TARGET_FMA4")
647          (eq_attr "isa" "fma") (symbol_ref "TARGET_FMA")
648         ]
649         (const_int 1)))
650
651 ;; Describe a user's asm statement.
652 (define_asm_attributes
653   [(set_attr "length" "128")
654    (set_attr "type" "multi")])
655
656 (define_code_iterator plusminus [plus minus])
657
658 (define_code_iterator sat_plusminus [ss_plus us_plus ss_minus us_minus])
659
660 ;; Base name for define_insn
661 (define_code_attr plusminus_insn
662   [(plus "add") (ss_plus "ssadd") (us_plus "usadd")
663    (minus "sub") (ss_minus "sssub") (us_minus "ussub")])
664
665 ;; Base name for insn mnemonic.
666 (define_code_attr plusminus_mnemonic
667   [(plus "add") (ss_plus "adds") (us_plus "addus")
668    (minus "sub") (ss_minus "subs") (us_minus "subus")])
669 (define_code_attr plusminus_carry_mnemonic
670   [(plus "adc") (minus "sbb")])
671
672 ;; Mark commutative operators as such in constraints.
673 (define_code_attr comm [(plus "%") (ss_plus "%") (us_plus "%")
674                         (minus "") (ss_minus "") (us_minus "")])
675
676 ;; Mapping of max and min
677 (define_code_iterator maxmin [smax smin umax umin])
678
679 ;; Mapping of signed max and min
680 (define_code_iterator smaxmin [smax smin])
681
682 ;; Mapping of unsigned max and min
683 (define_code_iterator umaxmin [umax umin])
684
685 ;; Base name for integer and FP insn mnemonic
686 (define_code_attr maxmin_int [(smax "maxs") (smin "mins")
687                               (umax "maxu") (umin "minu")])
688 (define_code_attr maxmin_float [(smax "max") (smin "min")])
689
690 ;; Mapping of logic operators
691 (define_code_iterator any_logic [and ior xor])
692 (define_code_iterator any_or [ior xor])
693
694 ;; Base name for insn mnemonic.
695 (define_code_attr logic [(and "and") (ior "or") (xor "xor")])
696
697 ;; Mapping of logic-shift operators
698 (define_code_iterator any_lshift [ashift lshiftrt])
699
700 ;; Mapping of shift-right operators
701 (define_code_iterator any_shiftrt [lshiftrt ashiftrt])
702
703 ;; Base name for define_insn
704 (define_code_attr shift_insn
705   [(ashift "ashl") (lshiftrt "lshr") (ashiftrt "ashr")])
706
707 ;; Base name for insn mnemonic.
708 (define_code_attr shift [(ashift "sll") (lshiftrt "shr") (ashiftrt "sar")])
709 (define_code_attr vshift [(ashift "sll") (lshiftrt "srl") (ashiftrt "sra")])
710
711 ;; Mapping of rotate operators
712 (define_code_iterator any_rotate [rotate rotatert])
713
714 ;; Base name for define_insn
715 (define_code_attr rotate_insn [(rotate "rotl") (rotatert "rotr")])
716
717 ;; Base name for insn mnemonic.
718 (define_code_attr rotate [(rotate "rol") (rotatert "ror")])
719
720 ;; Mapping of abs neg operators
721 (define_code_iterator absneg [abs neg])
722
723 ;; Base name for x87 insn mnemonic.
724 (define_code_attr absneg_mnemonic [(abs "abs") (neg "chs")])
725
726 ;; Used in signed and unsigned widening multiplications.
727 (define_code_iterator any_extend [sign_extend zero_extend])
728
729 ;; Prefix for insn menmonic.
730 (define_code_attr sgnprefix [(sign_extend "i") (zero_extend "")])
731
732 ;; Prefix for define_insn
733 (define_code_attr u [(sign_extend "") (zero_extend "u")])
734 (define_code_attr s [(sign_extend "s") (zero_extend "u")])
735
736 ;; All integer modes.
737 (define_mode_iterator SWI1248x [QI HI SI DI])
738
739 ;; All integer modes without QImode.
740 (define_mode_iterator SWI248x [HI SI DI])
741
742 ;; All integer modes without QImode and HImode.
743 (define_mode_iterator SWI48x [SI DI])
744
745 ;; All integer modes without SImode and DImode.
746 (define_mode_iterator SWI12 [QI HI])
747
748 ;; All integer modes without DImode.
749 (define_mode_iterator SWI124 [QI HI SI])
750
751 ;; All integer modes without QImode and DImode.
752 (define_mode_iterator SWI24 [HI SI])
753
754 ;; Single word integer modes.
755 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
756
757 ;; Single word integer modes without QImode.
758 (define_mode_iterator SWI248 [HI SI (DI "TARGET_64BIT")])
759
760 ;; Single word integer modes without QImode and HImode.
761 (define_mode_iterator SWI48 [SI (DI "TARGET_64BIT")])
762
763 ;; All math-dependant single and double word integer modes.
764 (define_mode_iterator SDWIM [(QI "TARGET_QIMODE_MATH")
765                              (HI "TARGET_HIMODE_MATH")
766                              SI DI (TI "TARGET_64BIT")])
767
768 ;; Math-dependant single word integer modes.
769 (define_mode_iterator SWIM [(QI "TARGET_QIMODE_MATH")
770                             (HI "TARGET_HIMODE_MATH")
771                             SI (DI "TARGET_64BIT")])
772
773 ;; Math-dependant integer modes without DImode.
774 (define_mode_iterator SWIM124 [(QI "TARGET_QIMODE_MATH")
775                                (HI "TARGET_HIMODE_MATH")
776                                SI])
777
778 ;; Math-dependant single word integer modes without QImode.
779 (define_mode_iterator SWIM248 [(HI "TARGET_HIMODE_MATH")
780                                SI (DI "TARGET_64BIT")])
781
782 ;; Double word integer modes.
783 (define_mode_iterator DWI [(DI "!TARGET_64BIT")
784                            (TI "TARGET_64BIT")])
785
786 ;; Double word integer modes as mode attribute.
787 (define_mode_attr DWI [(SI "DI") (DI "TI")])
788 (define_mode_attr dwi [(SI "di") (DI "ti")])
789
790 ;; Half mode for double word integer modes.
791 (define_mode_iterator DWIH [(SI "!TARGET_64BIT")
792                             (DI "TARGET_64BIT")])
793
794 ;; Instruction suffix for integer modes.
795 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
796
797 ;; Pointer size prefix for integer modes (Intel asm dialect)
798 (define_mode_attr iptrsize [(QI "BYTE")
799                             (HI "WORD")
800                             (SI "DWORD")
801                             (DI "QWORD")])
802
803 ;; Register class for integer modes.
804 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
805
806 ;; Immediate operand constraint for integer modes.
807 (define_mode_attr i [(QI "n") (HI "n") (SI "e") (DI "e")])
808
809 ;; General operand constraint for word modes.
810 (define_mode_attr g [(QI "qmn") (HI "rmn") (SI "rme") (DI "rme")])
811
812 ;; Immediate operand constraint for double integer modes.
813 (define_mode_attr di [(SI "nF") (DI "e")])
814
815 ;; Immediate operand constraint for shifts.
816 (define_mode_attr S [(QI "I") (HI "I") (SI "I") (DI "J") (TI "O")])
817
818 ;; General operand predicate for integer modes.
819 (define_mode_attr general_operand
820         [(QI "general_operand")
821          (HI "general_operand")
822          (SI "x86_64_general_operand")
823          (DI "x86_64_general_operand")
824          (TI "x86_64_general_operand")])
825
826 ;; General sign/zero extend operand predicate for integer modes.
827 (define_mode_attr general_szext_operand
828         [(QI "general_operand")
829          (HI "general_operand")
830          (SI "x86_64_szext_general_operand")
831          (DI "x86_64_szext_general_operand")])
832
833 ;; Immediate operand predicate for integer modes.
834 (define_mode_attr immediate_operand
835         [(QI "immediate_operand")
836          (HI "immediate_operand")
837          (SI "x86_64_immediate_operand")
838          (DI "x86_64_immediate_operand")])
839
840 ;; Nonmemory operand predicate for integer modes.
841 (define_mode_attr nonmemory_operand
842         [(QI "nonmemory_operand")
843          (HI "nonmemory_operand")
844          (SI "x86_64_nonmemory_operand")
845          (DI "x86_64_nonmemory_operand")])
846
847 ;; Operand predicate for shifts.
848 (define_mode_attr shift_operand
849         [(QI "nonimmediate_operand")
850          (HI "nonimmediate_operand")
851          (SI "nonimmediate_operand")
852          (DI "shiftdi_operand")
853          (TI "register_operand")])
854
855 ;; Operand predicate for shift argument.
856 (define_mode_attr shift_immediate_operand
857         [(QI "const_1_to_31_operand")
858          (HI "const_1_to_31_operand")
859          (SI "const_1_to_31_operand")
860          (DI "const_1_to_63_operand")])
861
862 ;; Input operand predicate for arithmetic left shifts.
863 (define_mode_attr ashl_input_operand
864         [(QI "nonimmediate_operand")
865          (HI "nonimmediate_operand")
866          (SI "nonimmediate_operand")
867          (DI "ashldi_input_operand")
868          (TI "reg_or_pm1_operand")])
869
870 ;; SSE and x87 SFmode and DFmode floating point modes
871 (define_mode_iterator MODEF [SF DF])
872
873 ;; All x87 floating point modes
874 (define_mode_iterator X87MODEF [SF DF XF])
875
876 ;; SSE instruction suffix for various modes
877 (define_mode_attr ssemodesuffix
878   [(SF "ss") (DF "sd")
879    (V8SF "ps") (V4DF "pd")
880    (V4SF "ps") (V2DF "pd")
881    (V16QI "b") (V8HI "w") (V4SI "d") (V2DI "q")
882    (V32QI "b") (V16HI "w") (V8SI "d") (V4DI "q")])
883
884 ;; SSE vector suffix for floating point modes
885 (define_mode_attr ssevecmodesuffix [(SF "ps") (DF "pd")])
886
887 ;; SSE vector mode corresponding to a scalar mode
888 (define_mode_attr ssevecmode
889   [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
890
891 ;; Instruction suffix for REX 64bit operators.
892 (define_mode_attr rex64suffix [(SI "") (DI "{q}")])
893
894 ;; This mode iterator allows :P to be used for patterns that operate on
895 ;; pointer-sized quantities.  Exactly one of the two alternatives will match.
896 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
897
898 ;; This mode iterator allows :PTR to be used for patterns that operate on
899 ;; ptr_mode sized quantities.
900 (define_mode_iterator PTR
901   [(SI "ptr_mode == SImode") (DI "ptr_mode == DImode")])
902 \f
903 ;; Scheduling descriptions
904
905 (include "pentium.md")
906 (include "ppro.md")
907 (include "k6.md")
908 (include "athlon.md")
909 (include "bdver1.md")
910 (include "geode.md")
911 (include "atom.md")
912 (include "core2.md")
913
914 \f
915 ;; Operand and operator predicates and constraints
916
917 (include "predicates.md")
918 (include "constraints.md")
919
920 \f
921 ;; Compare and branch/compare and store instructions.
922
923 (define_expand "cbranch<mode>4"
924   [(set (reg:CC FLAGS_REG)
925         (compare:CC (match_operand:SDWIM 1 "nonimmediate_operand" "")
926                     (match_operand:SDWIM 2 "<general_operand>" "")))
927    (set (pc) (if_then_else
928                (match_operator 0 "ordered_comparison_operator"
929                 [(reg:CC FLAGS_REG) (const_int 0)])
930                (label_ref (match_operand 3 "" ""))
931                (pc)))]
932   ""
933 {
934   if (MEM_P (operands[1]) && MEM_P (operands[2]))
935     operands[1] = force_reg (<MODE>mode, operands[1]);
936   ix86_expand_branch (GET_CODE (operands[0]),
937                       operands[1], operands[2], operands[3]);
938   DONE;
939 })
940
941 (define_expand "cstore<mode>4"
942   [(set (reg:CC FLAGS_REG)
943         (compare:CC (match_operand:SWIM 2 "nonimmediate_operand" "")
944                     (match_operand:SWIM 3 "<general_operand>" "")))
945    (set (match_operand:QI 0 "register_operand" "")
946         (match_operator 1 "ordered_comparison_operator"
947           [(reg:CC FLAGS_REG) (const_int 0)]))]
948   ""
949 {
950   if (MEM_P (operands[2]) && MEM_P (operands[3]))
951     operands[2] = force_reg (<MODE>mode, operands[2]);
952   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
953                      operands[2], operands[3]);
954   DONE;
955 })
956
957 (define_expand "cmp<mode>_1"
958   [(set (reg:CC FLAGS_REG)
959         (compare:CC (match_operand:SWI48 0 "nonimmediate_operand" "")
960                     (match_operand:SWI48 1 "<general_operand>" "")))])
961
962 (define_insn "*cmp<mode>_ccno_1"
963   [(set (reg FLAGS_REG)
964         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>,?m<r>")
965                  (match_operand:SWI 1 "const0_operand" "")))]
966   "ix86_match_ccmode (insn, CCNOmode)"
967   "@
968    test{<imodesuffix>}\t%0, %0
969    cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
970   [(set_attr "type" "test,icmp")
971    (set_attr "length_immediate" "0,1")
972    (set_attr "mode" "<MODE>")])
973
974 (define_insn "*cmp<mode>_1"
975   [(set (reg FLAGS_REG)
976         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
977                  (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m")))]
978   "ix86_match_ccmode (insn, CCmode)"
979   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
980   [(set_attr "type" "icmp")
981    (set_attr "mode" "<MODE>")])
982
983 (define_insn "*cmp<mode>_minus_1"
984   [(set (reg FLAGS_REG)
985         (compare
986           (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
987                      (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
988           (const_int 0)))]
989   "ix86_match_ccmode (insn, CCGOCmode)"
990   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
991   [(set_attr "type" "icmp")
992    (set_attr "mode" "<MODE>")])
993
994 (define_insn "*cmpqi_ext_1"
995   [(set (reg FLAGS_REG)
996         (compare
997           (match_operand:QI 0 "general_operand" "Qm")
998           (subreg:QI
999             (zero_extract:SI
1000               (match_operand 1 "ext_register_operand" "Q")
1001               (const_int 8)
1002               (const_int 8)) 0)))]
1003   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1004   "cmp{b}\t{%h1, %0|%0, %h1}"
1005   [(set_attr "type" "icmp")
1006    (set_attr "mode" "QI")])
1007
1008 (define_insn "*cmpqi_ext_1_rex64"
1009   [(set (reg FLAGS_REG)
1010         (compare
1011           (match_operand:QI 0 "register_operand" "Q")
1012           (subreg:QI
1013             (zero_extract:SI
1014               (match_operand 1 "ext_register_operand" "Q")
1015               (const_int 8)
1016               (const_int 8)) 0)))]
1017   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1018   "cmp{b}\t{%h1, %0|%0, %h1}"
1019   [(set_attr "type" "icmp")
1020    (set_attr "mode" "QI")])
1021
1022 (define_insn "*cmpqi_ext_2"
1023   [(set (reg FLAGS_REG)
1024         (compare
1025           (subreg:QI
1026             (zero_extract:SI
1027               (match_operand 0 "ext_register_operand" "Q")
1028               (const_int 8)
1029               (const_int 8)) 0)
1030           (match_operand:QI 1 "const0_operand" "")))]
1031   "ix86_match_ccmode (insn, CCNOmode)"
1032   "test{b}\t%h0, %h0"
1033   [(set_attr "type" "test")
1034    (set_attr "length_immediate" "0")
1035    (set_attr "mode" "QI")])
1036
1037 (define_expand "cmpqi_ext_3"
1038   [(set (reg:CC FLAGS_REG)
1039         (compare:CC
1040           (subreg:QI
1041             (zero_extract:SI
1042               (match_operand 0 "ext_register_operand" "")
1043               (const_int 8)
1044               (const_int 8)) 0)
1045           (match_operand:QI 1 "immediate_operand" "")))])
1046
1047 (define_insn "*cmpqi_ext_3_insn"
1048   [(set (reg FLAGS_REG)
1049         (compare
1050           (subreg:QI
1051             (zero_extract:SI
1052               (match_operand 0 "ext_register_operand" "Q")
1053               (const_int 8)
1054               (const_int 8)) 0)
1055           (match_operand:QI 1 "general_operand" "Qmn")))]
1056   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1057   "cmp{b}\t{%1, %h0|%h0, %1}"
1058   [(set_attr "type" "icmp")
1059    (set_attr "modrm" "1")
1060    (set_attr "mode" "QI")])
1061
1062 (define_insn "*cmpqi_ext_3_insn_rex64"
1063   [(set (reg FLAGS_REG)
1064         (compare
1065           (subreg:QI
1066             (zero_extract:SI
1067               (match_operand 0 "ext_register_operand" "Q")
1068               (const_int 8)
1069               (const_int 8)) 0)
1070           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
1071   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1072   "cmp{b}\t{%1, %h0|%h0, %1}"
1073   [(set_attr "type" "icmp")
1074    (set_attr "modrm" "1")
1075    (set_attr "mode" "QI")])
1076
1077 (define_insn "*cmpqi_ext_4"
1078   [(set (reg FLAGS_REG)
1079         (compare
1080           (subreg:QI
1081             (zero_extract:SI
1082               (match_operand 0 "ext_register_operand" "Q")
1083               (const_int 8)
1084               (const_int 8)) 0)
1085           (subreg:QI
1086             (zero_extract:SI
1087               (match_operand 1 "ext_register_operand" "Q")
1088               (const_int 8)
1089               (const_int 8)) 0)))]
1090   "ix86_match_ccmode (insn, CCmode)"
1091   "cmp{b}\t{%h1, %h0|%h0, %h1}"
1092   [(set_attr "type" "icmp")
1093    (set_attr "mode" "QI")])
1094
1095 ;; These implement float point compares.
1096 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
1097 ;; which would allow mix and match FP modes on the compares.  Which is what
1098 ;; the old patterns did, but with many more of them.
1099
1100 (define_expand "cbranchxf4"
1101   [(set (reg:CC FLAGS_REG)
1102         (compare:CC (match_operand:XF 1 "nonmemory_operand" "")
1103                     (match_operand:XF 2 "nonmemory_operand" "")))
1104    (set (pc) (if_then_else
1105               (match_operator 0 "ix86_fp_comparison_operator"
1106                [(reg:CC FLAGS_REG)
1107                 (const_int 0)])
1108               (label_ref (match_operand 3 "" ""))
1109               (pc)))]
1110   "TARGET_80387"
1111 {
1112   ix86_expand_branch (GET_CODE (operands[0]),
1113                       operands[1], operands[2], operands[3]);
1114   DONE;
1115 })
1116
1117 (define_expand "cstorexf4"
1118   [(set (reg:CC FLAGS_REG)
1119         (compare:CC (match_operand:XF 2 "nonmemory_operand" "")
1120                     (match_operand:XF 3 "nonmemory_operand" "")))
1121    (set (match_operand:QI 0 "register_operand" "")
1122               (match_operator 1 "ix86_fp_comparison_operator"
1123                [(reg:CC FLAGS_REG)
1124                 (const_int 0)]))]
1125   "TARGET_80387"
1126 {
1127   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1128                      operands[2], operands[3]);
1129   DONE;
1130 })
1131
1132 (define_expand "cbranch<mode>4"
1133   [(set (reg:CC FLAGS_REG)
1134         (compare:CC (match_operand:MODEF 1 "cmp_fp_expander_operand" "")
1135                     (match_operand:MODEF 2 "cmp_fp_expander_operand" "")))
1136    (set (pc) (if_then_else
1137               (match_operator 0 "ix86_fp_comparison_operator"
1138                [(reg:CC FLAGS_REG)
1139                 (const_int 0)])
1140               (label_ref (match_operand 3 "" ""))
1141               (pc)))]
1142   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1143 {
1144   ix86_expand_branch (GET_CODE (operands[0]),
1145                       operands[1], operands[2], operands[3]);
1146   DONE;
1147 })
1148
1149 (define_expand "cstore<mode>4"
1150   [(set (reg:CC FLAGS_REG)
1151         (compare:CC (match_operand:MODEF 2 "cmp_fp_expander_operand" "")
1152                     (match_operand:MODEF 3 "cmp_fp_expander_operand" "")))
1153    (set (match_operand:QI 0 "register_operand" "")
1154               (match_operator 1 "ix86_fp_comparison_operator"
1155                [(reg:CC FLAGS_REG)
1156                 (const_int 0)]))]
1157   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1158 {
1159   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1160                      operands[2], operands[3]);
1161   DONE;
1162 })
1163
1164 (define_expand "cbranchcc4"
1165   [(set (pc) (if_then_else
1166               (match_operator 0 "comparison_operator"
1167                [(match_operand 1 "flags_reg_operand" "")
1168                 (match_operand 2 "const0_operand" "")])
1169               (label_ref (match_operand 3 "" ""))
1170               (pc)))]
1171   ""
1172 {
1173   ix86_expand_branch (GET_CODE (operands[0]),
1174                       operands[1], operands[2], operands[3]);
1175   DONE;
1176 })
1177
1178 (define_expand "cstorecc4"
1179   [(set (match_operand:QI 0 "register_operand" "")
1180               (match_operator 1 "comparison_operator"
1181                [(match_operand 2 "flags_reg_operand" "")
1182                 (match_operand 3 "const0_operand" "")]))]
1183   ""
1184 {
1185   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1186                      operands[2], operands[3]);
1187   DONE;
1188 })
1189
1190
1191 ;; FP compares, step 1:
1192 ;; Set the FP condition codes.
1193 ;;
1194 ;; CCFPmode     compare with exceptions
1195 ;; CCFPUmode    compare with no exceptions
1196
1197 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1198 ;; used to manage the reg stack popping would not be preserved.
1199
1200 (define_insn "*cmpfp_0"
1201   [(set (match_operand:HI 0 "register_operand" "=a")
1202         (unspec:HI
1203           [(compare:CCFP
1204              (match_operand 1 "register_operand" "f")
1205              (match_operand 2 "const0_operand" ""))]
1206         UNSPEC_FNSTSW))]
1207   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1208    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1209   "* return output_fp_compare (insn, operands, false, false);"
1210   [(set_attr "type" "multi")
1211    (set_attr "unit" "i387")
1212    (set (attr "mode")
1213      (cond [(match_operand:SF 1 "" "")
1214               (const_string "SF")
1215             (match_operand:DF 1 "" "")
1216               (const_string "DF")
1217            ]
1218            (const_string "XF")))])
1219
1220 (define_insn_and_split "*cmpfp_0_cc"
1221   [(set (reg:CCFP FLAGS_REG)
1222         (compare:CCFP
1223           (match_operand 1 "register_operand" "f")
1224           (match_operand 2 "const0_operand" "")))
1225    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1226   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1227    && TARGET_SAHF && !TARGET_CMOVE
1228    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1229   "#"
1230   "&& reload_completed"
1231   [(set (match_dup 0)
1232         (unspec:HI
1233           [(compare:CCFP (match_dup 1)(match_dup 2))]
1234         UNSPEC_FNSTSW))
1235    (set (reg:CC FLAGS_REG)
1236         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1237   ""
1238   [(set_attr "type" "multi")
1239    (set_attr "unit" "i387")
1240    (set (attr "mode")
1241      (cond [(match_operand:SF 1 "" "")
1242               (const_string "SF")
1243             (match_operand:DF 1 "" "")
1244               (const_string "DF")
1245            ]
1246            (const_string "XF")))])
1247
1248 (define_insn "*cmpfp_xf"
1249   [(set (match_operand:HI 0 "register_operand" "=a")
1250         (unspec:HI
1251           [(compare:CCFP
1252              (match_operand:XF 1 "register_operand" "f")
1253              (match_operand:XF 2 "register_operand" "f"))]
1254           UNSPEC_FNSTSW))]
1255   "TARGET_80387"
1256   "* return output_fp_compare (insn, operands, false, false);"
1257   [(set_attr "type" "multi")
1258    (set_attr "unit" "i387")
1259    (set_attr "mode" "XF")])
1260
1261 (define_insn_and_split "*cmpfp_xf_cc"
1262   [(set (reg:CCFP FLAGS_REG)
1263         (compare:CCFP
1264           (match_operand:XF 1 "register_operand" "f")
1265           (match_operand:XF 2 "register_operand" "f")))
1266    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1267   "TARGET_80387
1268    && TARGET_SAHF && !TARGET_CMOVE"
1269   "#"
1270   "&& reload_completed"
1271   [(set (match_dup 0)
1272         (unspec:HI
1273           [(compare:CCFP (match_dup 1)(match_dup 2))]
1274         UNSPEC_FNSTSW))
1275    (set (reg:CC FLAGS_REG)
1276         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1277   ""
1278   [(set_attr "type" "multi")
1279    (set_attr "unit" "i387")
1280    (set_attr "mode" "XF")])
1281
1282 (define_insn "*cmpfp_<mode>"
1283   [(set (match_operand:HI 0 "register_operand" "=a")
1284         (unspec:HI
1285           [(compare:CCFP
1286              (match_operand:MODEF 1 "register_operand" "f")
1287              (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1288           UNSPEC_FNSTSW))]
1289   "TARGET_80387"
1290   "* return output_fp_compare (insn, operands, false, false);"
1291   [(set_attr "type" "multi")
1292    (set_attr "unit" "i387")
1293    (set_attr "mode" "<MODE>")])
1294
1295 (define_insn_and_split "*cmpfp_<mode>_cc"
1296   [(set (reg:CCFP FLAGS_REG)
1297         (compare:CCFP
1298           (match_operand:MODEF 1 "register_operand" "f")
1299           (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1300    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1301   "TARGET_80387
1302    && TARGET_SAHF && !TARGET_CMOVE"
1303   "#"
1304   "&& reload_completed"
1305   [(set (match_dup 0)
1306         (unspec:HI
1307           [(compare:CCFP (match_dup 1)(match_dup 2))]
1308         UNSPEC_FNSTSW))
1309    (set (reg:CC FLAGS_REG)
1310         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1311   ""
1312   [(set_attr "type" "multi")
1313    (set_attr "unit" "i387")
1314    (set_attr "mode" "<MODE>")])
1315
1316 (define_insn "*cmpfp_u"
1317   [(set (match_operand:HI 0 "register_operand" "=a")
1318         (unspec:HI
1319           [(compare:CCFPU
1320              (match_operand 1 "register_operand" "f")
1321              (match_operand 2 "register_operand" "f"))]
1322           UNSPEC_FNSTSW))]
1323   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1324    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1325   "* return output_fp_compare (insn, operands, false, true);"
1326   [(set_attr "type" "multi")
1327    (set_attr "unit" "i387")
1328    (set (attr "mode")
1329      (cond [(match_operand:SF 1 "" "")
1330               (const_string "SF")
1331             (match_operand:DF 1 "" "")
1332               (const_string "DF")
1333            ]
1334            (const_string "XF")))])
1335
1336 (define_insn_and_split "*cmpfp_u_cc"
1337   [(set (reg:CCFPU FLAGS_REG)
1338         (compare:CCFPU
1339           (match_operand 1 "register_operand" "f")
1340           (match_operand 2 "register_operand" "f")))
1341    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1342   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1343    && TARGET_SAHF && !TARGET_CMOVE
1344    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1345   "#"
1346   "&& reload_completed"
1347   [(set (match_dup 0)
1348         (unspec:HI
1349           [(compare:CCFPU (match_dup 1)(match_dup 2))]
1350         UNSPEC_FNSTSW))
1351    (set (reg:CC FLAGS_REG)
1352         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1353   ""
1354   [(set_attr "type" "multi")
1355    (set_attr "unit" "i387")
1356    (set (attr "mode")
1357      (cond [(match_operand:SF 1 "" "")
1358               (const_string "SF")
1359             (match_operand:DF 1 "" "")
1360               (const_string "DF")
1361            ]
1362            (const_string "XF")))])
1363
1364 (define_insn "*cmpfp_<mode>"
1365   [(set (match_operand:HI 0 "register_operand" "=a")
1366         (unspec:HI
1367           [(compare:CCFP
1368              (match_operand 1 "register_operand" "f")
1369              (match_operator 3 "float_operator"
1370                [(match_operand:SWI24 2 "memory_operand" "m")]))]
1371           UNSPEC_FNSTSW))]
1372   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1373    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1374    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1375   "* return output_fp_compare (insn, operands, false, false);"
1376   [(set_attr "type" "multi")
1377    (set_attr "unit" "i387")
1378    (set_attr "fp_int_src" "true")
1379    (set_attr "mode" "<MODE>")])
1380
1381 (define_insn_and_split "*cmpfp_<mode>_cc"
1382   [(set (reg:CCFP FLAGS_REG)
1383         (compare:CCFP
1384           (match_operand 1 "register_operand" "f")
1385           (match_operator 3 "float_operator"
1386             [(match_operand:SWI24 2 "memory_operand" "m")])))
1387    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1388   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1389    && TARGET_SAHF && !TARGET_CMOVE
1390    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1391    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1392   "#"
1393   "&& reload_completed"
1394   [(set (match_dup 0)
1395         (unspec:HI
1396           [(compare:CCFP
1397              (match_dup 1)
1398              (match_op_dup 3 [(match_dup 2)]))]
1399         UNSPEC_FNSTSW))
1400    (set (reg:CC FLAGS_REG)
1401         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1402   ""
1403   [(set_attr "type" "multi")
1404    (set_attr "unit" "i387")
1405    (set_attr "fp_int_src" "true")
1406    (set_attr "mode" "<MODE>")])
1407
1408 ;; FP compares, step 2
1409 ;; Move the fpsw to ax.
1410
1411 (define_insn "x86_fnstsw_1"
1412   [(set (match_operand:HI 0 "register_operand" "=a")
1413         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1414   "TARGET_80387"
1415   "fnstsw\t%0"
1416   [(set (attr "length")
1417         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
1418    (set_attr "mode" "SI")
1419    (set_attr "unit" "i387")])
1420
1421 ;; FP compares, step 3
1422 ;; Get ax into flags, general case.
1423
1424 (define_insn "x86_sahf_1"
1425   [(set (reg:CC FLAGS_REG)
1426         (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1427                    UNSPEC_SAHF))]
1428   "TARGET_SAHF"
1429 {
1430 #ifndef HAVE_AS_IX86_SAHF
1431   if (TARGET_64BIT)
1432     return ASM_BYTE "0x9e";
1433   else
1434 #endif
1435   return "sahf";
1436 }
1437   [(set_attr "length" "1")
1438    (set_attr "athlon_decode" "vector")
1439    (set_attr "amdfam10_decode" "direct")
1440    (set_attr "bdver1_decode" "direct")
1441    (set_attr "mode" "SI")])
1442
1443 ;; Pentium Pro can do steps 1 through 3 in one go.
1444 ;; comi*, ucomi*, fcomi*, ficomi*, fucomi*
1445 ;; (these i387 instructions set flags directly)
1446 (define_insn "*cmpfp_i_mixed"
1447   [(set (reg:CCFP FLAGS_REG)
1448         (compare:CCFP (match_operand 0 "register_operand" "f,x")
1449                       (match_operand 1 "nonimmediate_operand" "f,xm")))]
1450   "TARGET_MIX_SSE_I387
1451    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1452    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1453   "* return output_fp_compare (insn, operands, true, false);"
1454   [(set_attr "type" "fcmp,ssecomi")
1455    (set_attr "prefix" "orig,maybe_vex")
1456    (set (attr "mode")
1457      (if_then_else (match_operand:SF 1 "" "")
1458         (const_string "SF")
1459         (const_string "DF")))
1460    (set (attr "prefix_rep")
1461         (if_then_else (eq_attr "type" "ssecomi")
1462                       (const_string "0")
1463                       (const_string "*")))
1464    (set (attr "prefix_data16")
1465         (cond [(eq_attr "type" "fcmp")
1466                  (const_string "*")
1467                (eq_attr "mode" "DF")
1468                  (const_string "1")
1469               ]
1470               (const_string "0")))
1471    (set_attr "athlon_decode" "vector")
1472    (set_attr "amdfam10_decode" "direct")
1473    (set_attr "bdver1_decode" "double")])
1474
1475 (define_insn "*cmpfp_i_sse"
1476   [(set (reg:CCFP FLAGS_REG)
1477         (compare:CCFP (match_operand 0 "register_operand" "x")
1478                       (match_operand 1 "nonimmediate_operand" "xm")))]
1479   "TARGET_SSE_MATH
1480    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1481    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1482   "* return output_fp_compare (insn, operands, true, false);"
1483   [(set_attr "type" "ssecomi")
1484    (set_attr "prefix" "maybe_vex")
1485    (set (attr "mode")
1486      (if_then_else (match_operand:SF 1 "" "")
1487         (const_string "SF")
1488         (const_string "DF")))
1489    (set_attr "prefix_rep" "0")
1490    (set (attr "prefix_data16")
1491         (if_then_else (eq_attr "mode" "DF")
1492                       (const_string "1")
1493                       (const_string "0")))
1494    (set_attr "athlon_decode" "vector")
1495    (set_attr "amdfam10_decode" "direct")
1496    (set_attr "bdver1_decode" "double")])
1497
1498 (define_insn "*cmpfp_i_i387"
1499   [(set (reg:CCFP FLAGS_REG)
1500         (compare:CCFP (match_operand 0 "register_operand" "f")
1501                       (match_operand 1 "register_operand" "f")))]
1502   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1503    && TARGET_CMOVE
1504    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1505    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1506   "* return output_fp_compare (insn, operands, true, false);"
1507   [(set_attr "type" "fcmp")
1508    (set (attr "mode")
1509      (cond [(match_operand:SF 1 "" "")
1510               (const_string "SF")
1511             (match_operand:DF 1 "" "")
1512               (const_string "DF")
1513            ]
1514            (const_string "XF")))
1515    (set_attr "athlon_decode" "vector")
1516    (set_attr "amdfam10_decode" "direct")
1517    (set_attr "bdver1_decode" "double")])
1518
1519 (define_insn "*cmpfp_iu_mixed"
1520   [(set (reg:CCFPU FLAGS_REG)
1521         (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1522                        (match_operand 1 "nonimmediate_operand" "f,xm")))]
1523   "TARGET_MIX_SSE_I387
1524    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1525    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1526   "* return output_fp_compare (insn, operands, true, true);"
1527   [(set_attr "type" "fcmp,ssecomi")
1528    (set_attr "prefix" "orig,maybe_vex")
1529    (set (attr "mode")
1530      (if_then_else (match_operand:SF 1 "" "")
1531         (const_string "SF")
1532         (const_string "DF")))
1533    (set (attr "prefix_rep")
1534         (if_then_else (eq_attr "type" "ssecomi")
1535                       (const_string "0")
1536                       (const_string "*")))
1537    (set (attr "prefix_data16")
1538         (cond [(eq_attr "type" "fcmp")
1539                  (const_string "*")
1540                (eq_attr "mode" "DF")
1541                  (const_string "1")
1542               ]
1543               (const_string "0")))
1544    (set_attr "athlon_decode" "vector")
1545    (set_attr "amdfam10_decode" "direct")
1546    (set_attr "bdver1_decode" "double")])
1547
1548 (define_insn "*cmpfp_iu_sse"
1549   [(set (reg:CCFPU FLAGS_REG)
1550         (compare:CCFPU (match_operand 0 "register_operand" "x")
1551                        (match_operand 1 "nonimmediate_operand" "xm")))]
1552   "TARGET_SSE_MATH
1553    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1554    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1555   "* return output_fp_compare (insn, operands, true, true);"
1556   [(set_attr "type" "ssecomi")
1557    (set_attr "prefix" "maybe_vex")
1558    (set (attr "mode")
1559      (if_then_else (match_operand:SF 1 "" "")
1560         (const_string "SF")
1561         (const_string "DF")))
1562    (set_attr "prefix_rep" "0")
1563    (set (attr "prefix_data16")
1564         (if_then_else (eq_attr "mode" "DF")
1565                       (const_string "1")
1566                       (const_string "0")))
1567    (set_attr "athlon_decode" "vector")
1568    (set_attr "amdfam10_decode" "direct")
1569    (set_attr "bdver1_decode" "double")])
1570
1571 (define_insn "*cmpfp_iu_387"
1572   [(set (reg:CCFPU FLAGS_REG)
1573         (compare:CCFPU (match_operand 0 "register_operand" "f")
1574                        (match_operand 1 "register_operand" "f")))]
1575   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1576    && TARGET_CMOVE
1577    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1578    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1579   "* return output_fp_compare (insn, operands, true, true);"
1580   [(set_attr "type" "fcmp")
1581    (set (attr "mode")
1582      (cond [(match_operand:SF 1 "" "")
1583               (const_string "SF")
1584             (match_operand:DF 1 "" "")
1585               (const_string "DF")
1586            ]
1587            (const_string "XF")))
1588    (set_attr "athlon_decode" "vector")
1589    (set_attr "amdfam10_decode" "direct")
1590    (set_attr "bdver1_decode" "direct")])
1591 \f
1592 ;; Push/pop instructions.
1593
1594 (define_insn "*push<mode>2"
1595   [(set (match_operand:DWI 0 "push_operand" "=<")
1596         (match_operand:DWI 1 "general_no_elim_operand" "riF*o"))]
1597   ""
1598   "#"
1599   [(set_attr "type" "multi")
1600    (set_attr "mode" "<MODE>")])
1601
1602 (define_split
1603   [(set (match_operand:TI 0 "push_operand" "")
1604         (match_operand:TI 1 "general_operand" ""))]
1605   "TARGET_64BIT && reload_completed
1606    && !SSE_REG_P (operands[1])"
1607   [(const_int 0)]
1608   "ix86_split_long_move (operands); DONE;")
1609
1610 (define_insn "*pushdi2_rex64"
1611   [(set (match_operand:DI 0 "push_operand" "=<,!<")
1612         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1613   "TARGET_64BIT"
1614   "@
1615    push{q}\t%1
1616    #"
1617   [(set_attr "type" "push,multi")
1618    (set_attr "mode" "DI")])
1619
1620 ;; Convert impossible pushes of immediate to existing instructions.
1621 ;; First try to get scratch register and go through it.  In case this
1622 ;; fails, push sign extended lower part first and then overwrite
1623 ;; upper part by 32bit move.
1624 (define_peephole2
1625   [(match_scratch:DI 2 "r")
1626    (set (match_operand:DI 0 "push_operand" "")
1627         (match_operand:DI 1 "immediate_operand" ""))]
1628   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1629    && !x86_64_immediate_operand (operands[1], DImode)"
1630   [(set (match_dup 2) (match_dup 1))
1631    (set (match_dup 0) (match_dup 2))])
1632
1633 ;; We need to define this as both peepholer and splitter for case
1634 ;; peephole2 pass is not run.
1635 ;; "&& 1" is needed to keep it from matching the previous pattern.
1636 (define_peephole2
1637   [(set (match_operand:DI 0 "push_operand" "")
1638         (match_operand:DI 1 "immediate_operand" ""))]
1639   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1640    && !x86_64_immediate_operand (operands[1], DImode) && 1"
1641   [(set (match_dup 0) (match_dup 1))
1642    (set (match_dup 2) (match_dup 3))]
1643 {
1644   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1645
1646   operands[1] = gen_lowpart (DImode, operands[2]);
1647   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1648                                                    GEN_INT (4)));
1649 })
1650
1651 (define_split
1652   [(set (match_operand:DI 0 "push_operand" "")
1653         (match_operand:DI 1 "immediate_operand" ""))]
1654   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1655                     ? epilogue_completed : reload_completed)
1656    && !symbolic_operand (operands[1], DImode)
1657    && !x86_64_immediate_operand (operands[1], DImode)"
1658   [(set (match_dup 0) (match_dup 1))
1659    (set (match_dup 2) (match_dup 3))]
1660 {
1661   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1662
1663   operands[1] = gen_lowpart (DImode, operands[2]);
1664   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1665                                                    GEN_INT (4)));
1666 })
1667
1668 (define_split
1669   [(set (match_operand:DI 0 "push_operand" "")
1670         (match_operand:DI 1 "general_operand" ""))]
1671   "!TARGET_64BIT && reload_completed
1672    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
1673   [(const_int 0)]
1674   "ix86_split_long_move (operands); DONE;")
1675
1676 (define_insn "*pushsi2"
1677   [(set (match_operand:SI 0 "push_operand" "=<")
1678         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1679   "!TARGET_64BIT"
1680   "push{l}\t%1"
1681   [(set_attr "type" "push")
1682    (set_attr "mode" "SI")])
1683
1684 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1685 ;; "push a byte/word".  But actually we use pushl, which has the effect
1686 ;; of rounding the amount pushed up to a word.
1687
1688 ;; For TARGET_64BIT we always round up to 8 bytes.
1689 (define_insn "*push<mode>2_rex64"
1690   [(set (match_operand:SWI124 0 "push_operand" "=X")
1691         (match_operand:SWI124 1 "nonmemory_no_elim_operand" "r<i>"))]
1692   "TARGET_64BIT"
1693   "push{q}\t%q1"
1694   [(set_attr "type" "push")
1695    (set_attr "mode" "DI")])
1696
1697 (define_insn "*push<mode>2"
1698   [(set (match_operand:SWI12 0 "push_operand" "=X")
1699         (match_operand:SWI12 1 "nonmemory_no_elim_operand" "rn"))]
1700   "!TARGET_64BIT"
1701   "push{l}\t%k1"
1702   [(set_attr "type" "push")
1703    (set_attr "mode" "SI")])
1704
1705 (define_insn "*push<mode>2_prologue"
1706   [(set (match_operand:P 0 "push_operand" "=<")
1707         (match_operand:P 1 "general_no_elim_operand" "r<i>*m"))
1708    (clobber (mem:BLK (scratch)))]
1709   ""
1710   "push{<imodesuffix>}\t%1"
1711   [(set_attr "type" "push")
1712    (set_attr "mode" "<MODE>")])
1713
1714 (define_insn "*pop<mode>1"
1715   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1716         (match_operand:P 1 "pop_operand" ">"))]
1717   ""
1718   "pop{<imodesuffix>}\t%0"
1719   [(set_attr "type" "pop")
1720    (set_attr "mode" "<MODE>")])
1721
1722 (define_insn "*pop<mode>1_epilogue"
1723   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1724         (match_operand:P 1 "pop_operand" ">"))
1725    (clobber (mem:BLK (scratch)))]
1726   ""
1727   "pop{<imodesuffix>}\t%0"
1728   [(set_attr "type" "pop")
1729    (set_attr "mode" "<MODE>")])
1730 \f
1731 ;; Move instructions.
1732
1733 (define_expand "movoi"
1734   [(set (match_operand:OI 0 "nonimmediate_operand" "")
1735         (match_operand:OI 1 "general_operand" ""))]
1736   "TARGET_AVX"
1737   "ix86_expand_move (OImode, operands); DONE;")
1738
1739 (define_expand "movti"
1740   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1741         (match_operand:TI 1 "nonimmediate_operand" ""))]
1742   "TARGET_64BIT || TARGET_SSE"
1743 {
1744   if (TARGET_64BIT)
1745     ix86_expand_move (TImode, operands);
1746   else if (push_operand (operands[0], TImode))
1747     ix86_expand_push (TImode, operands[1]);
1748   else
1749     ix86_expand_vector_move (TImode, operands);
1750   DONE;
1751 })
1752
1753 ;; This expands to what emit_move_complex would generate if we didn't
1754 ;; have a movti pattern.  Having this avoids problems with reload on
1755 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
1756 ;; to have around all the time.
1757 (define_expand "movcdi"
1758   [(set (match_operand:CDI 0 "nonimmediate_operand" "")
1759         (match_operand:CDI 1 "general_operand" ""))]
1760   ""
1761 {
1762   if (push_operand (operands[0], CDImode))
1763     emit_move_complex_push (CDImode, operands[0], operands[1]);
1764   else
1765     emit_move_complex_parts (operands[0], operands[1]);
1766   DONE;
1767 })
1768
1769 (define_expand "mov<mode>"
1770   [(set (match_operand:SWI1248x 0 "nonimmediate_operand" "")
1771         (match_operand:SWI1248x 1 "general_operand" ""))]
1772   ""
1773   "ix86_expand_move (<MODE>mode, operands); DONE;")
1774
1775 (define_insn "*mov<mode>_xor"
1776   [(set (match_operand:SWI48 0 "register_operand" "=r")
1777         (match_operand:SWI48 1 "const0_operand" ""))
1778    (clobber (reg:CC FLAGS_REG))]
1779   "reload_completed"
1780   "xor{l}\t%k0, %k0"
1781   [(set_attr "type" "alu1")
1782    (set_attr "mode" "SI")
1783    (set_attr "length_immediate" "0")])
1784
1785 (define_insn "*mov<mode>_or"
1786   [(set (match_operand:SWI48 0 "register_operand" "=r")
1787         (match_operand:SWI48 1 "const_int_operand" ""))
1788    (clobber (reg:CC FLAGS_REG))]
1789   "reload_completed
1790    && operands[1] == constm1_rtx"
1791   "or{<imodesuffix>}\t{%1, %0|%0, %1}"
1792   [(set_attr "type" "alu1")
1793    (set_attr "mode" "<MODE>")
1794    (set_attr "length_immediate" "1")])
1795
1796 (define_insn "*movoi_internal_avx"
1797   [(set (match_operand:OI 0 "nonimmediate_operand" "=x,x,m")
1798         (match_operand:OI 1 "vector_move_operand" "C,xm,x"))]
1799   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1800 {
1801   switch (which_alternative)
1802     {
1803     case 0:
1804       return standard_sse_constant_opcode (insn, operands[1]);
1805     case 1:
1806     case 2:
1807       if (misaligned_operand (operands[0], OImode)
1808           || misaligned_operand (operands[1], OImode))
1809         return "vmovdqu\t{%1, %0|%0, %1}";
1810       else
1811         return "vmovdqa\t{%1, %0|%0, %1}";
1812     default:
1813       gcc_unreachable ();
1814     }
1815 }
1816   [(set_attr "type" "sselog1,ssemov,ssemov")
1817    (set_attr "prefix" "vex")
1818    (set_attr "mode" "OI")])
1819
1820 (define_insn "*movti_internal_rex64"
1821   [(set (match_operand:TI 0 "nonimmediate_operand" "=!r,o,x,x,xm")
1822         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
1823   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1824 {
1825   switch (which_alternative)
1826     {
1827     case 0:
1828     case 1:
1829       return "#";
1830     case 2:
1831       return standard_sse_constant_opcode (insn, operands[1]);
1832     case 3:
1833     case 4:
1834       /* TDmode values are passed as TImode on the stack.  Moving them
1835          to stack may result in unaligned memory access.  */
1836       if (misaligned_operand (operands[0], TImode)
1837           || misaligned_operand (operands[1], TImode))
1838         {
1839           if (get_attr_mode (insn) == MODE_V4SF)
1840             return "%vmovups\t{%1, %0|%0, %1}";
1841           else
1842             return "%vmovdqu\t{%1, %0|%0, %1}";
1843         }
1844       else
1845         {
1846           if (get_attr_mode (insn) == MODE_V4SF)
1847             return "%vmovaps\t{%1, %0|%0, %1}";
1848           else
1849             return "%vmovdqa\t{%1, %0|%0, %1}";
1850         }
1851     default:
1852       gcc_unreachable ();
1853     }
1854 }
1855   [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
1856    (set_attr "prefix" "*,*,maybe_vex,maybe_vex,maybe_vex")
1857    (set (attr "mode")
1858         (cond [(eq_attr "alternative" "2,3")
1859                  (if_then_else
1860                    (match_test "optimize_function_for_size_p (cfun)")
1861                    (const_string "V4SF")
1862                    (const_string "TI"))
1863                (eq_attr "alternative" "4")
1864                  (if_then_else
1865                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
1866                         (match_test "optimize_function_for_size_p (cfun)"))
1867                    (const_string "V4SF")
1868                    (const_string "TI"))]
1869                (const_string "DI")))])
1870
1871 (define_split
1872   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1873         (match_operand:TI 1 "general_operand" ""))]
1874   "reload_completed
1875    && !SSE_REG_P (operands[0]) && !SSE_REG_P (operands[1])"
1876   [(const_int 0)]
1877   "ix86_split_long_move (operands); DONE;")
1878
1879 (define_insn "*movti_internal_sse"
1880   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
1881         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
1882   "TARGET_SSE && !TARGET_64BIT
1883    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1884 {
1885   switch (which_alternative)
1886     {
1887     case 0:
1888       return standard_sse_constant_opcode (insn, operands[1]);
1889     case 1:
1890     case 2:
1891       /* TDmode values are passed as TImode on the stack.  Moving them
1892          to stack may result in unaligned memory access.  */
1893       if (misaligned_operand (operands[0], TImode)
1894           || misaligned_operand (operands[1], TImode))
1895         {
1896           if (get_attr_mode (insn) == MODE_V4SF)
1897             return "%vmovups\t{%1, %0|%0, %1}";
1898           else
1899             return "%vmovdqu\t{%1, %0|%0, %1}";
1900         }
1901       else
1902         {
1903           if (get_attr_mode (insn) == MODE_V4SF)
1904             return "%vmovaps\t{%1, %0|%0, %1}";
1905           else
1906             return "%vmovdqa\t{%1, %0|%0, %1}";
1907         }
1908     default:
1909       gcc_unreachable ();
1910     }
1911 }
1912   [(set_attr "type" "sselog1,ssemov,ssemov")
1913    (set_attr "prefix" "maybe_vex")
1914    (set (attr "mode")
1915         (cond [(ior (not (match_test "TARGET_SSE2"))
1916                     (match_test "optimize_function_for_size_p (cfun)"))
1917                  (const_string "V4SF")
1918                (and (eq_attr "alternative" "2")
1919                     (match_test "TARGET_SSE_TYPELESS_STORES"))
1920                  (const_string "V4SF")]
1921               (const_string "TI")))])
1922
1923 (define_insn "*movdi_internal_rex64"
1924   [(set (match_operand:DI 0 "nonimmediate_operand"
1925           "=r,r  ,r,m ,!o,*y,m*y,?*y,?r ,?*Ym,*x,m ,*x,*x,?r ,?*Yi,?*x,?*Ym")
1926         (match_operand:DI 1 "general_operand"
1927           "Z ,rem,i,re,n ,C ,*y ,m  ,*Ym,r   ,C ,*x,*x,m ,*Yi,r   ,*Ym,*x"))]
1928   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1929 {
1930   switch (get_attr_type (insn))
1931     {
1932     case TYPE_SSECVT:
1933       if (SSE_REG_P (operands[0]))
1934         return "movq2dq\t{%1, %0|%0, %1}";
1935       else
1936         return "movdq2q\t{%1, %0|%0, %1}";
1937
1938     case TYPE_SSEMOV:
1939       if (get_attr_mode (insn) == MODE_TI)
1940         return "%vmovdqa\t{%1, %0|%0, %1}";
1941       /* Handle broken assemblers that require movd instead of movq.  */
1942       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1943         return "%vmovd\t{%1, %0|%0, %1}";
1944       else
1945         return "%vmovq\t{%1, %0|%0, %1}";
1946
1947     case TYPE_MMXMOV:
1948       /* Handle broken assemblers that require movd instead of movq.  */
1949       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1950         return "movd\t{%1, %0|%0, %1}";
1951       else
1952         return "movq\t{%1, %0|%0, %1}";
1953
1954     case TYPE_SSELOG1:
1955       return standard_sse_constant_opcode (insn, operands[1]);
1956
1957     case TYPE_MMX:
1958       return "pxor\t%0, %0";
1959
1960     case TYPE_MULTI:
1961       return "#";
1962
1963     case TYPE_LEA:
1964       return "lea{q}\t{%E1, %0|%0, %E1}";
1965
1966     default:
1967       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1968       if (get_attr_mode (insn) == MODE_SI)
1969         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1970       else if (which_alternative == 2)
1971         return "movabs{q}\t{%1, %0|%0, %1}";
1972       else if (ix86_use_lea_for_mov (insn, operands))
1973         return "lea{q}\t{%E1, %0|%0, %E1}";
1974       else
1975         return "mov{q}\t{%1, %0|%0, %1}";
1976     }
1977 }
1978   [(set (attr "type")
1979      (cond [(eq_attr "alternative" "4")
1980               (const_string "multi")
1981             (eq_attr "alternative" "5")
1982               (const_string "mmx")
1983             (eq_attr "alternative" "6,7,8,9")
1984               (const_string "mmxmov")
1985             (eq_attr "alternative" "10")
1986               (const_string "sselog1")
1987             (eq_attr "alternative" "11,12,13,14,15")
1988               (const_string "ssemov")
1989             (eq_attr "alternative" "16,17")
1990               (const_string "ssecvt")
1991             (match_operand 1 "pic_32bit_operand" "")
1992               (const_string "lea")
1993            ]
1994            (const_string "imov")))
1995    (set (attr "modrm")
1996      (if_then_else
1997        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
1998          (const_string "0")
1999          (const_string "*")))
2000    (set (attr "length_immediate")
2001      (if_then_else
2002        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
2003          (const_string "8")
2004          (const_string "*")))
2005    (set (attr "prefix_rex")
2006      (if_then_else (eq_attr "alternative" "8,9")
2007        (const_string "1")
2008        (const_string "*")))
2009    (set (attr "prefix_data16")
2010      (if_then_else (eq_attr "alternative" "11")
2011        (const_string "1")
2012        (const_string "*")))
2013    (set (attr "prefix")
2014      (if_then_else (eq_attr "alternative" "10,11,12,13,14,15")
2015        (const_string "maybe_vex")
2016        (const_string "orig")))
2017    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,TI,DI,TI,DI,DI,DI,DI,DI")])
2018
2019 ;; Reload patterns to support multi-word load/store
2020 ;; with non-offsetable address.
2021 (define_expand "reload_noff_store"
2022   [(parallel [(match_operand 0 "memory_operand" "=m")
2023               (match_operand 1 "register_operand" "r")
2024               (match_operand:DI 2 "register_operand" "=&r")])]
2025   "TARGET_64BIT"
2026 {
2027   rtx mem = operands[0];
2028   rtx addr = XEXP (mem, 0);
2029
2030   emit_move_insn (operands[2], addr);
2031   mem = replace_equiv_address_nv (mem, operands[2]);
2032
2033   emit_insn (gen_rtx_SET (VOIDmode, mem, operands[1]));
2034   DONE;
2035 })
2036
2037 (define_expand "reload_noff_load"
2038   [(parallel [(match_operand 0 "register_operand" "=r")
2039               (match_operand 1 "memory_operand" "m")
2040               (match_operand:DI 2 "register_operand" "=r")])]
2041   "TARGET_64BIT"
2042 {
2043   rtx mem = operands[1];
2044   rtx addr = XEXP (mem, 0);
2045
2046   emit_move_insn (operands[2], addr);
2047   mem = replace_equiv_address_nv (mem, operands[2]);
2048
2049   emit_insn (gen_rtx_SET (VOIDmode, operands[0], mem));
2050   DONE;
2051 })
2052
2053 ;; Convert impossible stores of immediate to existing instructions.
2054 ;; First try to get scratch register and go through it.  In case this
2055 ;; fails, move by 32bit parts.
2056 (define_peephole2
2057   [(match_scratch:DI 2 "r")
2058    (set (match_operand:DI 0 "memory_operand" "")
2059         (match_operand:DI 1 "immediate_operand" ""))]
2060   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2061    && !x86_64_immediate_operand (operands[1], DImode)"
2062   [(set (match_dup 2) (match_dup 1))
2063    (set (match_dup 0) (match_dup 2))])
2064
2065 ;; We need to define this as both peepholer and splitter for case
2066 ;; peephole2 pass is not run.
2067 ;; "&& 1" is needed to keep it from matching the previous pattern.
2068 (define_peephole2
2069   [(set (match_operand:DI 0 "memory_operand" "")
2070         (match_operand:DI 1 "immediate_operand" ""))]
2071   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2072    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2073   [(set (match_dup 2) (match_dup 3))
2074    (set (match_dup 4) (match_dup 5))]
2075   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2076
2077 (define_split
2078   [(set (match_operand:DI 0 "memory_operand" "")
2079         (match_operand:DI 1 "immediate_operand" ""))]
2080   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2081                     ? epilogue_completed : reload_completed)
2082    && !symbolic_operand (operands[1], DImode)
2083    && !x86_64_immediate_operand (operands[1], DImode)"
2084   [(set (match_dup 2) (match_dup 3))
2085    (set (match_dup 4) (match_dup 5))]
2086   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2087
2088 (define_insn "*movdi_internal"
2089   [(set (match_operand:DI 0 "nonimmediate_operand"
2090           "=r  ,o  ,*y,m*y,*y,*x,m ,*x,*x,*x,m ,*x,*x,?*x,?*Ym")
2091         (match_operand:DI 1 "general_operand"
2092           "riFo,riF,C ,*y ,m ,C ,*x,*x,m ,C ,*x,*x,m ,*Ym,*x"))]
2093   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2094 {
2095   switch (get_attr_type (insn))
2096     {
2097     case TYPE_SSECVT:
2098       if (SSE_REG_P (operands[0]))
2099         return "movq2dq\t{%1, %0|%0, %1}";
2100       else
2101         return "movdq2q\t{%1, %0|%0, %1}";
2102
2103     case TYPE_SSEMOV:
2104       switch (get_attr_mode (insn))
2105         {
2106         case MODE_TI:
2107           return "%vmovdqa\t{%1, %0|%0, %1}";
2108         case MODE_DI:
2109            return "%vmovq\t{%1, %0|%0, %1}";
2110         case MODE_V4SF:
2111           return "movaps\t{%1, %0|%0, %1}";
2112         case MODE_V2SF:
2113           return "movlps\t{%1, %0|%0, %1}";
2114         default:
2115           gcc_unreachable ();
2116         }
2117
2118     case TYPE_MMXMOV:
2119       return "movq\t{%1, %0|%0, %1}";
2120
2121     case TYPE_SSELOG1:
2122       return standard_sse_constant_opcode (insn, operands[1]);
2123
2124     case TYPE_MMX:
2125       return "pxor\t%0, %0";
2126
2127     case TYPE_MULTI:
2128       return "#";
2129
2130     default:
2131       gcc_unreachable ();
2132     }
2133 }
2134   [(set (attr "isa")
2135      (cond [(eq_attr "alternative" "5,6,7,8,13,14")
2136               (const_string "sse2")
2137             (eq_attr "alternative" "9,10,11,12")
2138               (const_string "noavx")
2139            ]
2140            (const_string "*")))
2141    (set (attr "type")
2142      (cond [(eq_attr "alternative" "0,1")
2143               (const_string "multi")
2144             (eq_attr "alternative" "2")
2145               (const_string "mmx")
2146             (eq_attr "alternative" "3,4")
2147               (const_string "mmxmov")
2148             (eq_attr "alternative" "5,9")
2149               (const_string "sselog1")
2150             (eq_attr "alternative" "13,14")
2151               (const_string "ssecvt")
2152            ]
2153            (const_string "ssemov")))
2154    (set (attr "prefix")
2155      (if_then_else (eq_attr "alternative" "5,6,7,8")
2156        (const_string "maybe_vex")
2157        (const_string "orig")))
2158    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF,DI,DI")])
2159
2160 (define_split
2161   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2162         (match_operand:DI 1 "general_operand" ""))]
2163   "!TARGET_64BIT && reload_completed
2164    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))
2165    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
2166   [(const_int 0)]
2167   "ix86_split_long_move (operands); DONE;")
2168
2169 (define_insn "*movsi_internal"
2170   [(set (match_operand:SI 0 "nonimmediate_operand"
2171                         "=r,m ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
2172         (match_operand:SI 1 "general_operand"
2173                         "g ,re,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r   ,m "))]
2174   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2175 {
2176   switch (get_attr_type (insn))
2177     {
2178     case TYPE_SSELOG1:
2179       return standard_sse_constant_opcode (insn, operands[1]);
2180
2181     case TYPE_SSEMOV:
2182       switch (get_attr_mode (insn))
2183         {
2184         case MODE_TI:
2185           return "%vmovdqa\t{%1, %0|%0, %1}";
2186         case MODE_V4SF:
2187           return "%vmovaps\t{%1, %0|%0, %1}";
2188         case MODE_SI:
2189           return "%vmovd\t{%1, %0|%0, %1}";
2190         case MODE_SF:
2191           return "%vmovss\t{%1, %0|%0, %1}";
2192         default:
2193           gcc_unreachable ();
2194         }
2195
2196     case TYPE_MMX:
2197       return "pxor\t%0, %0";
2198
2199     case TYPE_MMXMOV:
2200       if (get_attr_mode (insn) == MODE_DI)
2201         return "movq\t{%1, %0|%0, %1}";
2202       return "movd\t{%1, %0|%0, %1}";
2203
2204     case TYPE_LEA:
2205       return "lea{l}\t{%E1, %0|%0, %E1}";
2206
2207     default:
2208       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2209       if (ix86_use_lea_for_mov (insn, operands))
2210         return "lea{l}\t{%E1, %0|%0, %E1}";
2211       else
2212         return "mov{l}\t{%1, %0|%0, %1}";
2213     }
2214 }
2215   [(set (attr "type")
2216      (cond [(eq_attr "alternative" "2")
2217               (const_string "mmx")
2218             (eq_attr "alternative" "3,4,5")
2219               (const_string "mmxmov")
2220             (eq_attr "alternative" "6")
2221               (const_string "sselog1")
2222             (eq_attr "alternative" "7,8,9,10,11")
2223               (const_string "ssemov")
2224             (match_operand 1 "pic_32bit_operand" "")
2225               (const_string "lea")
2226            ]
2227            (const_string "imov")))
2228    (set (attr "prefix")
2229      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5")
2230        (const_string "orig")
2231        (const_string "maybe_vex")))
2232    (set (attr "prefix_data16")
2233      (if_then_else (and (eq_attr "type" "ssemov") (eq_attr "mode" "SI"))
2234        (const_string "1")
2235        (const_string "*")))
2236    (set (attr "mode")
2237      (cond [(eq_attr "alternative" "2,3")
2238               (const_string "DI")
2239             (eq_attr "alternative" "6,7")
2240               (if_then_else
2241                 (not (match_test "TARGET_SSE2"))
2242                 (const_string "V4SF")
2243                 (const_string "TI"))
2244             (and (eq_attr "alternative" "8,9,10,11")
2245                  (not (match_test "TARGET_SSE2")))
2246               (const_string "SF")
2247            ]
2248            (const_string "SI")))])
2249
2250 (define_insn "*movhi_internal"
2251   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
2252         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
2253   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2254 {
2255   switch (get_attr_type (insn))
2256     {
2257     case TYPE_IMOVX:
2258       /* movzwl is faster than movw on p2 due to partial word stalls,
2259          though not as fast as an aligned movl.  */
2260       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
2261     default:
2262       if (get_attr_mode (insn) == MODE_SI)
2263         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2264       else
2265         return "mov{w}\t{%1, %0|%0, %1}";
2266     }
2267 }
2268   [(set (attr "type")
2269      (cond [(match_test "optimize_function_for_size_p (cfun)")
2270               (const_string "imov")
2271             (and (eq_attr "alternative" "0")
2272                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2273                       (not (match_test "TARGET_HIMODE_MATH"))))
2274               (const_string "imov")
2275             (and (eq_attr "alternative" "1,2")
2276                  (match_operand:HI 1 "aligned_operand" ""))
2277               (const_string "imov")
2278             (and (match_test "TARGET_MOVX")
2279                  (eq_attr "alternative" "0,2"))
2280               (const_string "imovx")
2281            ]
2282            (const_string "imov")))
2283     (set (attr "mode")
2284       (cond [(eq_attr "type" "imovx")
2285                (const_string "SI")
2286              (and (eq_attr "alternative" "1,2")
2287                   (match_operand:HI 1 "aligned_operand" ""))
2288                (const_string "SI")
2289              (and (eq_attr "alternative" "0")
2290                   (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2291                        (not (match_test "TARGET_HIMODE_MATH"))))
2292                (const_string "SI")
2293             ]
2294             (const_string "HI")))])
2295
2296 ;; Situation is quite tricky about when to choose full sized (SImode) move
2297 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
2298 ;; partial register dependency machines (such as AMD Athlon), where QImode
2299 ;; moves issue extra dependency and for partial register stalls machines
2300 ;; that don't use QImode patterns (and QImode move cause stall on the next
2301 ;; instruction).
2302 ;;
2303 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
2304 ;; register stall machines with, where we use QImode instructions, since
2305 ;; partial register stall can be caused there.  Then we use movzx.
2306 (define_insn "*movqi_internal"
2307   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
2308         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
2309   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2310 {
2311   switch (get_attr_type (insn))
2312     {
2313     case TYPE_IMOVX:
2314       gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
2315       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
2316     default:
2317       if (get_attr_mode (insn) == MODE_SI)
2318         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2319       else
2320         return "mov{b}\t{%1, %0|%0, %1}";
2321     }
2322 }
2323   [(set (attr "type")
2324      (cond [(and (eq_attr "alternative" "5")
2325                  (not (match_operand:QI 1 "aligned_operand" "")))
2326               (const_string "imovx")
2327             (match_test "optimize_function_for_size_p (cfun)")
2328               (const_string "imov")
2329             (and (eq_attr "alternative" "3")
2330                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2331                       (not (match_test "TARGET_QIMODE_MATH"))))
2332               (const_string "imov")
2333             (eq_attr "alternative" "3,5")
2334               (const_string "imovx")
2335             (and (match_test "TARGET_MOVX")
2336                  (eq_attr "alternative" "2"))
2337               (const_string "imovx")
2338            ]
2339            (const_string "imov")))
2340    (set (attr "mode")
2341       (cond [(eq_attr "alternative" "3,4,5")
2342                (const_string "SI")
2343              (eq_attr "alternative" "6")
2344                (const_string "QI")
2345              (eq_attr "type" "imovx")
2346                (const_string "SI")
2347              (and (eq_attr "type" "imov")
2348                   (and (eq_attr "alternative" "0,1")
2349                        (and (match_test "TARGET_PARTIAL_REG_DEPENDENCY")
2350                             (and (not (match_test "optimize_function_for_size_p (cfun)"))
2351                                  (not (match_test "TARGET_PARTIAL_REG_STALL"))))))
2352                (const_string "SI")
2353              ;; Avoid partial register stalls when not using QImode arithmetic
2354              (and (eq_attr "type" "imov")
2355                   (and (eq_attr "alternative" "0,1")
2356                        (and (match_test "TARGET_PARTIAL_REG_STALL")
2357                             (not (match_test "TARGET_QIMODE_MATH")))))
2358                (const_string "SI")
2359            ]
2360            (const_string "QI")))])
2361
2362 ;; Stores and loads of ax to arbitrary constant address.
2363 ;; We fake an second form of instruction to force reload to load address
2364 ;; into register when rax is not available
2365 (define_insn "*movabs<mode>_1"
2366   [(set (mem:SWI1248x (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2367         (match_operand:SWI1248x 1 "nonmemory_operand" "a,r<i>"))]
2368   "TARGET_LP64 && ix86_check_movabs (insn, 0)"
2369   "@
2370    movabs{<imodesuffix>}\t{%1, %P0|%P0, %1}
2371    mov{<imodesuffix>}\t{%1, %a0|%a0, %1}"
2372   [(set_attr "type" "imov")
2373    (set_attr "modrm" "0,*")
2374    (set_attr "length_address" "8,0")
2375    (set_attr "length_immediate" "0,*")
2376    (set_attr "memory" "store")
2377    (set_attr "mode" "<MODE>")])
2378
2379 (define_insn "*movabs<mode>_2"
2380   [(set (match_operand:SWI1248x 0 "register_operand" "=a,r")
2381         (mem:SWI1248x (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2382   "TARGET_LP64 && ix86_check_movabs (insn, 1)"
2383   "@
2384    movabs{<imodesuffix>}\t{%P1, %0|%0, %P1}
2385    mov{<imodesuffix>}\t{%a1, %0|%0, %a1}"
2386   [(set_attr "type" "imov")
2387    (set_attr "modrm" "0,*")
2388    (set_attr "length_address" "8,0")
2389    (set_attr "length_immediate" "0")
2390    (set_attr "memory" "load")
2391    (set_attr "mode" "<MODE>")])
2392
2393 (define_insn "*swap<mode>"
2394   [(set (match_operand:SWI48 0 "register_operand" "+r")
2395         (match_operand:SWI48 1 "register_operand" "+r"))
2396    (set (match_dup 1)
2397         (match_dup 0))]
2398   ""
2399   "xchg{<imodesuffix>}\t%1, %0"
2400   [(set_attr "type" "imov")
2401    (set_attr "mode" "<MODE>")
2402    (set_attr "pent_pair" "np")
2403    (set_attr "athlon_decode" "vector")
2404    (set_attr "amdfam10_decode" "double")
2405    (set_attr "bdver1_decode" "double")])
2406
2407 (define_insn "*swap<mode>_1"
2408   [(set (match_operand:SWI12 0 "register_operand" "+r")
2409         (match_operand:SWI12 1 "register_operand" "+r"))
2410    (set (match_dup 1)
2411         (match_dup 0))]
2412   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
2413   "xchg{l}\t%k1, %k0"
2414   [(set_attr "type" "imov")
2415    (set_attr "mode" "SI")
2416    (set_attr "pent_pair" "np")
2417    (set_attr "athlon_decode" "vector")
2418    (set_attr "amdfam10_decode" "double")
2419    (set_attr "bdver1_decode" "double")])
2420
2421 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL
2422 ;; is disabled for AMDFAM10
2423 (define_insn "*swap<mode>_2"
2424   [(set (match_operand:SWI12 0 "register_operand" "+<r>")
2425         (match_operand:SWI12 1 "register_operand" "+<r>"))
2426    (set (match_dup 1)
2427         (match_dup 0))]
2428   "TARGET_PARTIAL_REG_STALL"
2429   "xchg{<imodesuffix>}\t%1, %0"
2430   [(set_attr "type" "imov")
2431    (set_attr "mode" "<MODE>")
2432    (set_attr "pent_pair" "np")
2433    (set_attr "athlon_decode" "vector")])
2434
2435 (define_expand "movstrict<mode>"
2436   [(set (strict_low_part (match_operand:SWI12 0 "nonimmediate_operand" ""))
2437         (match_operand:SWI12 1 "general_operand" ""))]
2438   ""
2439 {
2440   if (TARGET_PARTIAL_REG_STALL && optimize_function_for_speed_p (cfun))
2441     FAIL;
2442   if (GET_CODE (operands[0]) == SUBREG
2443       && GET_MODE_CLASS (GET_MODE (SUBREG_REG (operands[0]))) != MODE_INT)
2444     FAIL;
2445   /* Don't generate memory->memory moves, go through a register */
2446   if (MEM_P (operands[0]) && MEM_P (operands[1]))
2447     operands[1] = force_reg (<MODE>mode, operands[1]);
2448 })
2449
2450 (define_insn "*movstrict<mode>_1"
2451   [(set (strict_low_part
2452           (match_operand:SWI12 0 "nonimmediate_operand" "+<r>m,<r>"))
2453         (match_operand:SWI12 1 "general_operand" "<r>n,m"))]
2454   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
2455    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2456   "mov{<imodesuffix>}\t{%1, %0|%0, %1}"
2457   [(set_attr "type" "imov")
2458    (set_attr "mode" "<MODE>")])
2459
2460 (define_insn "*movstrict<mode>_xor"
2461   [(set (strict_low_part (match_operand:SWI12 0 "register_operand" "+<r>"))
2462         (match_operand:SWI12 1 "const0_operand" ""))
2463    (clobber (reg:CC FLAGS_REG))]
2464   "reload_completed"
2465   "xor{<imodesuffix>}\t%0, %0"
2466   [(set_attr "type" "alu1")
2467    (set_attr "mode" "<MODE>")
2468    (set_attr "length_immediate" "0")])
2469
2470 (define_insn "*mov<mode>_extv_1"
2471   [(set (match_operand:SWI24 0 "register_operand" "=R")
2472         (sign_extract:SWI24 (match_operand 1 "ext_register_operand" "Q")
2473                             (const_int 8)
2474                             (const_int 8)))]
2475   ""
2476   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
2477   [(set_attr "type" "imovx")
2478    (set_attr "mode" "SI")])
2479
2480 (define_insn "*movqi_extv_1_rex64"
2481   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2482         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2483                          (const_int 8)
2484                          (const_int 8)))]
2485   "TARGET_64BIT"
2486 {
2487   switch (get_attr_type (insn))
2488     {
2489     case TYPE_IMOVX:
2490       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2491     default:
2492       return "mov{b}\t{%h1, %0|%0, %h1}";
2493     }
2494 }
2495   [(set (attr "type")
2496      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2497                         (match_test "TARGET_MOVX"))
2498         (const_string "imovx")
2499         (const_string "imov")))
2500    (set (attr "mode")
2501      (if_then_else (eq_attr "type" "imovx")
2502         (const_string "SI")
2503         (const_string "QI")))])
2504
2505 (define_insn "*movqi_extv_1"
2506   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
2507         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2508                          (const_int 8)
2509                          (const_int 8)))]
2510   "!TARGET_64BIT"
2511 {
2512   switch (get_attr_type (insn))
2513     {
2514     case TYPE_IMOVX:
2515       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2516     default:
2517       return "mov{b}\t{%h1, %0|%0, %h1}";
2518     }
2519 }
2520   [(set (attr "type")
2521      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2522                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2523                              (match_test "TARGET_MOVX")))
2524         (const_string "imovx")
2525         (const_string "imov")))
2526    (set (attr "mode")
2527      (if_then_else (eq_attr "type" "imovx")
2528         (const_string "SI")
2529         (const_string "QI")))])
2530
2531 (define_insn "*mov<mode>_extzv_1"
2532   [(set (match_operand:SWI48 0 "register_operand" "=R")
2533         (zero_extract:SWI48 (match_operand 1 "ext_register_operand" "Q")
2534                             (const_int 8)
2535                             (const_int 8)))]
2536   ""
2537   "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
2538   [(set_attr "type" "imovx")
2539    (set_attr "mode" "SI")])
2540
2541 (define_insn "*movqi_extzv_2_rex64"
2542   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2543         (subreg:QI
2544           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2545                            (const_int 8)
2546                            (const_int 8)) 0))]
2547   "TARGET_64BIT"
2548 {
2549   switch (get_attr_type (insn))
2550     {
2551     case TYPE_IMOVX:
2552       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2553     default:
2554       return "mov{b}\t{%h1, %0|%0, %h1}";
2555     }
2556 }
2557   [(set (attr "type")
2558      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2559                         (match_test "TARGET_MOVX"))
2560         (const_string "imovx")
2561         (const_string "imov")))
2562    (set (attr "mode")
2563      (if_then_else (eq_attr "type" "imovx")
2564         (const_string "SI")
2565         (const_string "QI")))])
2566
2567 (define_insn "*movqi_extzv_2"
2568   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2569         (subreg:QI
2570           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2571                            (const_int 8)
2572                            (const_int 8)) 0))]
2573   "!TARGET_64BIT"
2574 {
2575   switch (get_attr_type (insn))
2576     {
2577     case TYPE_IMOVX:
2578       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2579     default:
2580       return "mov{b}\t{%h1, %0|%0, %h1}";
2581     }
2582 }
2583   [(set (attr "type")
2584      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2585                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2586                              (match_test "TARGET_MOVX")))
2587         (const_string "imovx")
2588         (const_string "imov")))
2589    (set (attr "mode")
2590      (if_then_else (eq_attr "type" "imovx")
2591         (const_string "SI")
2592         (const_string "QI")))])
2593
2594 (define_expand "mov<mode>_insv_1"
2595   [(set (zero_extract:SWI48 (match_operand 0 "ext_register_operand" "")
2596                             (const_int 8)
2597                             (const_int 8))
2598         (match_operand:SWI48 1 "nonmemory_operand" ""))])
2599
2600 (define_insn "*mov<mode>_insv_1_rex64"
2601   [(set (zero_extract:SWI48x (match_operand 0 "ext_register_operand" "+Q")
2602                              (const_int 8)
2603                              (const_int 8))
2604         (match_operand:SWI48x 1 "nonmemory_operand" "Qn"))]
2605   "TARGET_64BIT"
2606 {
2607   if (CONST_INT_P (operands[1]))
2608     operands[1] = simplify_gen_subreg (QImode, operands[1], <MODE>mode, 0);
2609   return "mov{b}\t{%b1, %h0|%h0, %b1}";
2610 }
2611   [(set_attr "type" "imov")
2612    (set_attr "mode" "QI")])
2613
2614 (define_insn "*movsi_insv_1"
2615   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2616                          (const_int 8)
2617                          (const_int 8))
2618         (match_operand:SI 1 "general_operand" "Qmn"))]
2619   "!TARGET_64BIT"
2620 {
2621   if (CONST_INT_P (operands[1]))
2622     operands[1] = simplify_gen_subreg (QImode, operands[1], SImode, 0);
2623   return "mov{b}\t{%b1, %h0|%h0, %b1}";
2624 }
2625   [(set_attr "type" "imov")
2626    (set_attr "mode" "QI")])
2627
2628 (define_insn "*movqi_insv_2"
2629   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2630                          (const_int 8)
2631                          (const_int 8))
2632         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2633                      (const_int 8)))]
2634   ""
2635   "mov{b}\t{%h1, %h0|%h0, %h1}"
2636   [(set_attr "type" "imov")
2637    (set_attr "mode" "QI")])
2638 \f
2639 ;; Floating point push instructions.
2640
2641 (define_insn "*pushtf"
2642   [(set (match_operand:TF 0 "push_operand" "=<,<,<")
2643         (match_operand:TF 1 "general_no_elim_operand" "x,Fo,*r"))]
2644   "TARGET_SSE2"
2645 {
2646   /* This insn should be already split before reg-stack.  */
2647   gcc_unreachable ();
2648 }
2649   [(set_attr "type" "multi")
2650    (set_attr "unit" "sse,*,*")
2651    (set_attr "mode" "TF,SI,SI")])
2652
2653 ;; %%% Kill this when call knows how to work this out.
2654 (define_split
2655   [(set (match_operand:TF 0 "push_operand" "")
2656         (match_operand:TF 1 "sse_reg_operand" ""))]
2657   "TARGET_SSE2 && reload_completed"
2658   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -16)))
2659    (set (mem:TF (reg:P SP_REG)) (match_dup 1))])
2660
2661 (define_insn "*pushxf"
2662   [(set (match_operand:XF 0 "push_operand" "=<,<")
2663         (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
2664   "optimize_function_for_speed_p (cfun)"
2665 {
2666   /* This insn should be already split before reg-stack.  */
2667   gcc_unreachable ();
2668 }
2669   [(set_attr "type" "multi")
2670    (set_attr "unit" "i387,*")
2671    (set_attr "mode" "XF,SI")])
2672
2673 ;; Size of pushxf is 3 (for sub) + 2 (for fstp) + memory operand size.
2674 ;; Size of pushxf using integer instructions is 3+3*memory operand size
2675 ;; Pushing using integer instructions is longer except for constants
2676 ;; and direct memory references (assuming that any given constant is pushed
2677 ;; only once, but this ought to be handled elsewhere).
2678
2679 (define_insn "*pushxf_nointeger"
2680   [(set (match_operand:XF 0 "push_operand" "=<,<")
2681         (match_operand:XF 1 "general_no_elim_operand" "f,*rFo"))]
2682   "optimize_function_for_size_p (cfun)"
2683 {
2684   /* This insn should be already split before reg-stack.  */
2685   gcc_unreachable ();
2686 }
2687   [(set_attr "type" "multi")
2688    (set_attr "unit" "i387,*")
2689    (set_attr "mode" "XF,SI")])
2690
2691 ;; %%% Kill this when call knows how to work this out.
2692 (define_split
2693   [(set (match_operand:XF 0 "push_operand" "")
2694         (match_operand:XF 1 "fp_register_operand" ""))]
2695   "reload_completed"
2696   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2697    (set (mem:XF (reg:P SP_REG)) (match_dup 1))]
2698   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
2699
2700 (define_insn "*pushdf_rex64"
2701   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2702         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFm,x"))]
2703   "TARGET_64BIT"
2704 {
2705   /* This insn should be already split before reg-stack.  */
2706   gcc_unreachable ();
2707 }
2708   [(set_attr "type" "multi")
2709    (set_attr "unit" "i387,*,*")
2710    (set_attr "mode" "DF,DI,DF")])
2711
2712 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2713 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2714 ;; On the average, pushdf using integers can be still shorter.
2715
2716 (define_insn "*pushdf"
2717   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2718         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFo,x"))]
2719   "!TARGET_64BIT"
2720 {
2721   /* This insn should be already split before reg-stack.  */
2722   gcc_unreachable ();
2723 }
2724   [(set_attr "isa" "*,*,sse2")
2725    (set_attr "type" "multi")
2726    (set_attr "unit" "i387,*,*")
2727    (set_attr "mode" "DF,DI,DF")])
2728
2729 ;; %%% Kill this when call knows how to work this out.
2730 (define_split
2731   [(set (match_operand:DF 0 "push_operand" "")
2732         (match_operand:DF 1 "any_fp_register_operand" ""))]
2733   "reload_completed"
2734   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
2735    (set (mem:DF (reg:P SP_REG)) (match_dup 1))])
2736
2737 (define_insn "*pushsf_rex64"
2738   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2739         (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2740   "TARGET_64BIT"
2741 {
2742   /* Anything else should be already split before reg-stack.  */
2743   gcc_assert (which_alternative == 1);
2744   return "push{q}\t%q1";
2745 }
2746   [(set_attr "type" "multi,push,multi")
2747    (set_attr "unit" "i387,*,*")
2748    (set_attr "mode" "SF,DI,SF")])
2749
2750 (define_insn "*pushsf"
2751   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2752         (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2753   "!TARGET_64BIT"
2754 {
2755   /* Anything else should be already split before reg-stack.  */
2756   gcc_assert (which_alternative == 1);
2757   return "push{l}\t%1";
2758 }
2759   [(set_attr "type" "multi,push,multi")
2760    (set_attr "unit" "i387,*,*")
2761    (set_attr "mode" "SF,SI,SF")])
2762
2763 ;; %%% Kill this when call knows how to work this out.
2764 (define_split
2765   [(set (match_operand:SF 0 "push_operand" "")
2766         (match_operand:SF 1 "any_fp_register_operand" ""))]
2767   "reload_completed"
2768   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2769    (set (mem:SF (reg:P SP_REG)) (match_dup 1))]
2770   "operands[2] = GEN_INT (-GET_MODE_SIZE (<P:MODE>mode));")
2771
2772 (define_split
2773   [(set (match_operand:SF 0 "push_operand" "")
2774         (match_operand:SF 1 "memory_operand" ""))]
2775   "reload_completed
2776    && (operands[2] = find_constant_src (insn))"
2777   [(set (match_dup 0) (match_dup 2))])
2778
2779 (define_split
2780   [(set (match_operand 0 "push_operand" "")
2781         (match_operand 1 "general_operand" ""))]
2782   "reload_completed
2783    && (GET_MODE (operands[0]) == TFmode
2784        || GET_MODE (operands[0]) == XFmode
2785        || GET_MODE (operands[0]) == DFmode)
2786    && !ANY_FP_REG_P (operands[1])"
2787   [(const_int 0)]
2788   "ix86_split_long_move (operands); DONE;")
2789 \f
2790 ;; Floating point move instructions.
2791
2792 (define_expand "movtf"
2793   [(set (match_operand:TF 0 "nonimmediate_operand" "")
2794         (match_operand:TF 1 "nonimmediate_operand" ""))]
2795   "TARGET_SSE2"
2796 {
2797   ix86_expand_move (TFmode, operands);
2798   DONE;
2799 })
2800
2801 (define_expand "mov<mode>"
2802   [(set (match_operand:X87MODEF 0 "nonimmediate_operand" "")
2803         (match_operand:X87MODEF 1 "general_operand" ""))]
2804   ""
2805   "ix86_expand_move (<MODE>mode, operands); DONE;")
2806
2807 (define_insn "*movtf_internal"
2808   [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?*r ,!o")
2809         (match_operand:TF 1 "general_operand"      "xm,x,C,*roF,F*r"))]
2810   "TARGET_SSE2
2811    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2812    && (!can_create_pseudo_p ()
2813        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2814        || GET_CODE (operands[1]) != CONST_DOUBLE
2815        || (optimize_function_for_size_p (cfun)
2816            && standard_sse_constant_p (operands[1])
2817            && !memory_operand (operands[0], TFmode))
2818        || (!TARGET_MEMORY_MISMATCH_STALL
2819            && memory_operand (operands[0], TFmode)))"
2820 {
2821   switch (which_alternative)
2822     {
2823     case 0:
2824     case 1:
2825       /* Handle misaligned load/store since we
2826          don't have movmisaligntf pattern. */
2827       if (misaligned_operand (operands[0], TFmode)
2828           || misaligned_operand (operands[1], TFmode))
2829         {
2830           if (get_attr_mode (insn) == MODE_V4SF)
2831             return "%vmovups\t{%1, %0|%0, %1}";
2832           else
2833             return "%vmovdqu\t{%1, %0|%0, %1}";
2834         }
2835       else
2836         {
2837           if (get_attr_mode (insn) == MODE_V4SF)
2838             return "%vmovaps\t{%1, %0|%0, %1}";
2839           else
2840             return "%vmovdqa\t{%1, %0|%0, %1}";
2841         }
2842
2843     case 2:
2844       return standard_sse_constant_opcode (insn, operands[1]);
2845
2846     case 3:
2847     case 4:
2848         return "#";
2849
2850     default:
2851       gcc_unreachable ();
2852     }
2853 }
2854   [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
2855    (set_attr "prefix" "maybe_vex,maybe_vex,maybe_vex,*,*")
2856    (set (attr "mode")
2857         (cond [(eq_attr "alternative" "0,2")
2858                  (if_then_else
2859                    (match_test "optimize_function_for_size_p (cfun)")
2860                    (const_string "V4SF")
2861                    (const_string "TI"))
2862                (eq_attr "alternative" "1")
2863                  (if_then_else
2864                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
2865                         (match_test "optimize_function_for_size_p (cfun)"))
2866                    (const_string "V4SF")
2867                    (const_string "TI"))]
2868                (const_string "DI")))])
2869
2870 ;; Possible store forwarding (partial memory) stall in alternative 4.
2871 (define_insn "*movxf_internal"
2872   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,?Yx*r ,!o")
2873         (match_operand:XF 1 "general_operand"      "fm,f,G,Yx*roF,FYx*r"))]
2874   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2875    && (!can_create_pseudo_p ()
2876        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2877        || GET_CODE (operands[1]) != CONST_DOUBLE
2878        || (optimize_function_for_size_p (cfun)
2879            && standard_80387_constant_p (operands[1]) > 0
2880            && !memory_operand (operands[0], XFmode))
2881        || (!TARGET_MEMORY_MISMATCH_STALL
2882            && memory_operand (operands[0], XFmode)))"
2883 {
2884   switch (which_alternative)
2885     {
2886     case 0:
2887     case 1:
2888       return output_387_reg_move (insn, operands);
2889
2890     case 2:
2891       return standard_80387_constant_opcode (operands[1]);
2892
2893     case 3:
2894     case 4:
2895       return "#";
2896
2897     default:
2898       gcc_unreachable ();
2899     }
2900 }
2901   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2902    (set_attr "mode" "XF,XF,XF,SI,SI")])
2903
2904 (define_insn "*movdf_internal_rex64"
2905   [(set (match_operand:DF 0 "nonimmediate_operand"
2906                 "=f,m,f,?r,?m,?r,!o,x,x,x,m,Yi,r ")
2907         (match_operand:DF 1 "general_operand"
2908                 "fm,f,G,rm,r ,F ,F ,C,x,m,x,r ,Yi"))]
2909   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2910    && (!can_create_pseudo_p ()
2911        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2912        || GET_CODE (operands[1]) != CONST_DOUBLE
2913        || (optimize_function_for_size_p (cfun)
2914            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
2915                 && standard_80387_constant_p (operands[1]) > 0)
2916                || (TARGET_SSE2 && TARGET_SSE_MATH
2917                    && standard_sse_constant_p (operands[1]))))
2918        || memory_operand (operands[0], DFmode))"
2919 {
2920   switch (which_alternative)
2921     {
2922     case 0:
2923     case 1:
2924       return output_387_reg_move (insn, operands);
2925
2926     case 2:
2927       return standard_80387_constant_opcode (operands[1]);
2928
2929     case 3:
2930     case 4:
2931       return "mov{q}\t{%1, %0|%0, %1}";
2932
2933     case 5:
2934       return "movabs{q}\t{%1, %0|%0, %1}";
2935
2936     case 6:
2937       return "#";
2938
2939     case 7:
2940       return standard_sse_constant_opcode (insn, operands[1]);
2941
2942     case 8:
2943     case 9:
2944     case 10:
2945       switch (get_attr_mode (insn))
2946         {
2947         case MODE_V2DF:
2948           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
2949             return "%vmovapd\t{%1, %0|%0, %1}";
2950         case MODE_V4SF:
2951           return "%vmovaps\t{%1, %0|%0, %1}";
2952
2953         case MODE_DI:
2954           return "%vmovq\t{%1, %0|%0, %1}";
2955         case MODE_DF:
2956           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
2957             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
2958           return "%vmovsd\t{%1, %0|%0, %1}";
2959         case MODE_V1DF:
2960           return "%vmovlpd\t{%1, %d0|%d0, %1}";
2961         case MODE_V2SF:
2962           return "%vmovlps\t{%1, %d0|%d0, %1}";
2963         default:
2964           gcc_unreachable ();
2965         }
2966
2967     case 11:
2968     case 12:
2969       /* Handle broken assemblers that require movd instead of movq.  */
2970       return "%vmovd\t{%1, %0|%0, %1}";
2971
2972     default:
2973       gcc_unreachable();
2974     }
2975 }
2976   [(set (attr "type")
2977         (cond [(eq_attr "alternative" "0,1,2")
2978                  (const_string "fmov")
2979                (eq_attr "alternative" "3,4,5")
2980                  (const_string "imov")
2981                (eq_attr "alternative" "6")
2982                  (const_string "multi")
2983                (eq_attr "alternative" "7")
2984                  (const_string "sselog1")
2985               ]
2986               (const_string "ssemov")))
2987    (set (attr "modrm")
2988      (if_then_else
2989        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
2990          (const_string "0")
2991          (const_string "*")))
2992    (set (attr "length_immediate")
2993      (if_then_else
2994        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
2995          (const_string "8")
2996          (const_string "*")))
2997    (set (attr "prefix")
2998      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5,6")
2999        (const_string "orig")
3000        (const_string "maybe_vex")))
3001    (set (attr "prefix_data16")
3002      (if_then_else (eq_attr "mode" "V1DF")
3003        (const_string "1")
3004        (const_string "*")))
3005    (set (attr "mode")
3006         (cond [(eq_attr "alternative" "0,1,2")
3007                  (const_string "DF")
3008                (eq_attr "alternative" "3,4,5,6,11,12")
3009                  (const_string "DI")
3010
3011                /* xorps is one byte shorter.  */
3012                (eq_attr "alternative" "7")
3013                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3014                           (const_string "V4SF")
3015                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3016                           (const_string "TI")
3017                        ]
3018                        (const_string "V2DF"))
3019
3020                /* For architectures resolving dependencies on
3021                   whole SSE registers use APD move to break dependency
3022                   chains, otherwise use short move to avoid extra work.
3023
3024                   movaps encodes one byte shorter.  */
3025                (eq_attr "alternative" "8")
3026                  (cond
3027                    [(match_test "optimize_function_for_size_p (cfun)")
3028                       (const_string "V4SF")
3029                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3030                       (const_string "V2DF")
3031                    ]
3032                    (const_string "DF"))
3033                /* For architectures resolving dependencies on register
3034                   parts we may avoid extra work to zero out upper part
3035                   of register.  */
3036                (eq_attr "alternative" "9")
3037                  (if_then_else
3038                    (match_test "TARGET_SSE_SPLIT_REGS")
3039                    (const_string "V1DF")
3040                    (const_string "DF"))
3041               ]
3042               (const_string "DF")))])
3043
3044 ;; Possible store forwarding (partial memory) stall in alternative 4.
3045 (define_insn "*movdf_internal"
3046   [(set (match_operand:DF 0 "nonimmediate_operand"
3047                 "=f,m,f,?Yd*r ,!o   ,x,x,x,m,*x,*x,*x,m")
3048         (match_operand:DF 1 "general_operand"
3049                 "fm,f,G,Yd*roF,FYd*r,C,x,m,x,C ,*x,m ,*x"))]
3050   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3051    && (!can_create_pseudo_p ()
3052        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3053        || GET_CODE (operands[1]) != CONST_DOUBLE
3054        || (optimize_function_for_size_p (cfun)
3055            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
3056                 && standard_80387_constant_p (operands[1]) > 0)
3057                || (TARGET_SSE2 && TARGET_SSE_MATH
3058                    && standard_sse_constant_p (operands[1])))
3059            && !memory_operand (operands[0], DFmode))
3060        || (!TARGET_MEMORY_MISMATCH_STALL
3061            && memory_operand (operands[0], DFmode)))"
3062 {
3063   switch (which_alternative)
3064     {
3065     case 0:
3066     case 1:
3067       return output_387_reg_move (insn, operands);
3068
3069     case 2:
3070       return standard_80387_constant_opcode (operands[1]);
3071
3072     case 3:
3073     case 4:
3074       return "#";
3075
3076     case 5:
3077     case 9:
3078       return standard_sse_constant_opcode (insn, operands[1]);
3079
3080     case 6:
3081     case 7:
3082     case 8:
3083     case 10:
3084     case 11:
3085     case 12:
3086       switch (get_attr_mode (insn))
3087         {
3088         case MODE_V2DF:
3089           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
3090             return "%vmovapd\t{%1, %0|%0, %1}";
3091         case MODE_V4SF:
3092           return "%vmovaps\t{%1, %0|%0, %1}";
3093
3094         case MODE_DI:
3095           return "%vmovq\t{%1, %0|%0, %1}";
3096         case MODE_DF:
3097           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
3098             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3099           return "%vmovsd\t{%1, %0|%0, %1}";
3100         case MODE_V1DF:
3101           return "%vmovlpd\t{%1, %d0|%d0, %1}";
3102         case MODE_V2SF:
3103           return "%vmovlps\t{%1, %d0|%d0, %1}";
3104         default:
3105           gcc_unreachable ();
3106         }
3107
3108     default:
3109       gcc_unreachable ();
3110     }
3111 }
3112   [(set (attr "isa")
3113      (if_then_else (eq_attr "alternative" "5,6,7,8")
3114        (const_string "sse2")
3115        (const_string "*")))
3116    (set (attr "type")
3117         (cond [(eq_attr "alternative" "0,1,2")
3118                  (const_string "fmov")
3119                (eq_attr "alternative" "3,4")
3120                  (const_string "multi")
3121                (eq_attr "alternative" "5,9")
3122                  (const_string "sselog1")
3123               ]
3124               (const_string "ssemov")))
3125    (set (attr "prefix")
3126      (if_then_else (eq_attr "alternative" "0,1,2,3,4")
3127        (const_string "orig")
3128        (const_string "maybe_vex")))
3129    (set (attr "prefix_data16")
3130      (if_then_else (eq_attr "mode" "V1DF")
3131        (const_string "1")
3132        (const_string "*")))
3133    (set (attr "mode")
3134         (cond [(eq_attr "alternative" "0,1,2")
3135                  (const_string "DF")
3136                (eq_attr "alternative" "3,4")
3137                  (const_string "SI")
3138
3139                /* For SSE1, we have many fewer alternatives.  */
3140                (not (match_test "TARGET_SSE2"))
3141                  (if_then_else
3142                    (eq_attr "alternative" "5,6,9,10")
3143                    (const_string "V4SF")
3144                    (const_string "V2SF"))
3145
3146                /* xorps is one byte shorter.  */
3147                (eq_attr "alternative" "5,9")
3148                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3149                           (const_string "V4SF")
3150                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3151                           (const_string "TI")
3152                        ]
3153                        (const_string "V2DF"))
3154
3155                /* For architectures resolving dependencies on
3156                   whole SSE registers use APD move to break dependency
3157                   chains, otherwise use short move to avoid extra work.
3158
3159                   movaps encodes one byte shorter.  */
3160                (eq_attr "alternative" "6,10")
3161                  (cond
3162                    [(match_test "optimize_function_for_size_p (cfun)")
3163                       (const_string "V4SF")
3164                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3165                       (const_string "V2DF")
3166                    ]
3167                    (const_string "DF"))
3168                /* For architectures resolving dependencies on register
3169                   parts we may avoid extra work to zero out upper part
3170                   of register.  */
3171                (eq_attr "alternative" "7,11")
3172                  (if_then_else
3173                    (match_test "TARGET_SSE_SPLIT_REGS")
3174                    (const_string "V1DF")
3175                    (const_string "DF"))
3176               ]
3177               (const_string "DF")))])
3178
3179 (define_insn "*movsf_internal"
3180   [(set (match_operand:SF 0 "nonimmediate_operand"
3181           "=f,m,f,?r ,?m,x,x,x,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
3182         (match_operand:SF 1 "general_operand"
3183           "fm,f,G,rmF,Fr,C,x,m,x,m  ,*y,*y ,r  ,Yi,r   ,*Ym"))]
3184   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3185    && (!can_create_pseudo_p ()
3186        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3187        || GET_CODE (operands[1]) != CONST_DOUBLE
3188        || (optimize_function_for_size_p (cfun)
3189            && ((!TARGET_SSE_MATH
3190                 && standard_80387_constant_p (operands[1]) > 0)
3191                || (TARGET_SSE_MATH
3192                    && standard_sse_constant_p (operands[1]))))
3193        || memory_operand (operands[0], SFmode))"
3194 {
3195   switch (which_alternative)
3196     {
3197     case 0:
3198     case 1:
3199       return output_387_reg_move (insn, operands);
3200
3201     case 2:
3202       return standard_80387_constant_opcode (operands[1]);
3203
3204     case 3:
3205     case 4:
3206       return "mov{l}\t{%1, %0|%0, %1}";
3207
3208     case 5:
3209       return standard_sse_constant_opcode (insn, operands[1]);
3210
3211     case 6:
3212       if (get_attr_mode (insn) == MODE_V4SF)
3213         return "%vmovaps\t{%1, %0|%0, %1}";
3214       if (TARGET_AVX)
3215         return "vmovss\t{%1, %0, %0|%0, %0, %1}";
3216
3217     case 7:
3218     case 8:
3219       return "%vmovss\t{%1, %0|%0, %1}";
3220
3221     case 9:
3222     case 10:
3223     case 14:
3224     case 15:
3225       return "movd\t{%1, %0|%0, %1}";
3226
3227     case 11:
3228       return "movq\t{%1, %0|%0, %1}";
3229
3230     case 12:
3231     case 13:
3232       return "%vmovd\t{%1, %0|%0, %1}";
3233
3234     default:
3235       gcc_unreachable ();
3236     }
3237 }
3238   [(set (attr "type")
3239         (cond [(eq_attr "alternative" "0,1,2")
3240                  (const_string "fmov")
3241                (eq_attr "alternative" "3,4")
3242                  (const_string "multi")
3243                (eq_attr "alternative" "5")
3244                  (const_string "sselog1")
3245                (eq_attr "alternative" "9,10,11,14,15")
3246                  (const_string "mmxmov")
3247               ]
3248               (const_string "ssemov")))
3249    (set (attr "prefix")
3250      (if_then_else (eq_attr "alternative" "5,6,7,8,12,13")
3251        (const_string "maybe_vex")
3252        (const_string "orig")))
3253    (set (attr "mode")
3254         (cond [(eq_attr "alternative" "3,4,9,10")
3255                  (const_string "SI")
3256                (eq_attr "alternative" "5")
3257                  (if_then_else
3258                    (and (and (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3259                              (match_test "TARGET_SSE2"))
3260                         (not (match_test "optimize_function_for_size_p (cfun)")))
3261                    (const_string "TI")
3262                    (const_string "V4SF"))
3263                /* For architectures resolving dependencies on
3264                   whole SSE registers use APS move to break dependency
3265                   chains, otherwise use short move to avoid extra work.
3266
3267                   Do the same for architectures resolving dependencies on
3268                   the parts.  While in DF mode it is better to always handle
3269                   just register parts, the SF mode is different due to lack
3270                   of instructions to load just part of the register.  It is
3271                   better to maintain the whole registers in single format
3272                   to avoid problems on using packed logical operations.  */
3273                (eq_attr "alternative" "6")
3274                  (if_then_else
3275                    (ior (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3276                         (match_test "TARGET_SSE_SPLIT_REGS"))
3277                    (const_string "V4SF")
3278                    (const_string "SF"))
3279                (eq_attr "alternative" "11")
3280                  (const_string "DI")]
3281                (const_string "SF")))])
3282
3283 (define_split
3284   [(set (match_operand 0 "any_fp_register_operand" "")
3285         (match_operand 1 "memory_operand" ""))]
3286   "reload_completed
3287    && (GET_MODE (operands[0]) == TFmode
3288        || GET_MODE (operands[0]) == XFmode
3289        || GET_MODE (operands[0]) == DFmode
3290        || GET_MODE (operands[0]) == SFmode)
3291    && (operands[2] = find_constant_src (insn))"
3292   [(set (match_dup 0) (match_dup 2))]
3293 {
3294   rtx c = operands[2];
3295   int r = REGNO (operands[0]);
3296
3297   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3298       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3299     FAIL;
3300 })
3301
3302 (define_split
3303   [(set (match_operand 0 "any_fp_register_operand" "")
3304         (float_extend (match_operand 1 "memory_operand" "")))]
3305   "reload_completed
3306    && (GET_MODE (operands[0]) == TFmode
3307        || GET_MODE (operands[0]) == XFmode
3308        || GET_MODE (operands[0]) == DFmode)
3309    && (operands[2] = find_constant_src (insn))"
3310   [(set (match_dup 0) (match_dup 2))]
3311 {
3312   rtx c = operands[2];
3313   int r = REGNO (operands[0]);
3314
3315   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3316       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3317     FAIL;
3318 })
3319
3320 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3321 (define_split
3322   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
3323         (match_operand:X87MODEF 1 "immediate_operand" ""))]
3324   "reload_completed
3325    && (standard_80387_constant_p (operands[1]) == 8
3326        || standard_80387_constant_p (operands[1]) == 9)"
3327   [(set (match_dup 0)(match_dup 1))
3328    (set (match_dup 0)
3329         (neg:X87MODEF (match_dup 0)))]
3330 {
3331   REAL_VALUE_TYPE r;
3332
3333   REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3334   if (real_isnegzero (&r))
3335     operands[1] = CONST0_RTX (<MODE>mode);
3336   else
3337     operands[1] = CONST1_RTX (<MODE>mode);
3338 })
3339
3340 (define_split
3341   [(set (match_operand 0 "nonimmediate_operand" "")
3342         (match_operand 1 "general_operand" ""))]
3343   "reload_completed
3344    && (GET_MODE (operands[0]) == TFmode
3345        || GET_MODE (operands[0]) == XFmode
3346        || GET_MODE (operands[0]) == DFmode)
3347    && !(ANY_FP_REG_P (operands[0]) || ANY_FP_REG_P (operands[1]))"
3348   [(const_int 0)]
3349   "ix86_split_long_move (operands); DONE;")
3350
3351 (define_insn "swapxf"
3352   [(set (match_operand:XF 0 "register_operand" "+f")
3353         (match_operand:XF 1 "register_operand" "+f"))
3354    (set (match_dup 1)
3355         (match_dup 0))]
3356   "TARGET_80387"
3357 {
3358   if (STACK_TOP_P (operands[0]))
3359     return "fxch\t%1";
3360   else
3361     return "fxch\t%0";
3362 }
3363   [(set_attr "type" "fxch")
3364    (set_attr "mode" "XF")])
3365
3366 (define_insn "*swap<mode>"
3367   [(set (match_operand:MODEF 0 "fp_register_operand" "+f")
3368         (match_operand:MODEF 1 "fp_register_operand" "+f"))
3369    (set (match_dup 1)
3370         (match_dup 0))]
3371   "TARGET_80387 || reload_completed"
3372 {
3373   if (STACK_TOP_P (operands[0]))
3374     return "fxch\t%1";
3375   else
3376     return "fxch\t%0";
3377 }
3378   [(set_attr "type" "fxch")
3379    (set_attr "mode" "<MODE>")])
3380 \f
3381 ;; Zero extension instructions
3382
3383 (define_expand "zero_extendsidi2"
3384   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3385         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3386   ""
3387 {
3388   if (!TARGET_64BIT)
3389     {
3390       emit_insn (gen_zero_extendsidi2_1 (operands[0], operands[1]));
3391       DONE;
3392     }
3393 })
3394
3395 (define_insn "*zero_extendsidi2_rex64"
3396   [(set (match_operand:DI 0 "nonimmediate_operand"  "=r,o,?*Ym,?*y,?*Yi,*x")
3397         (zero_extend:DI
3398          (match_operand:SI 1 "nonimmediate_operand" "rm,0,r   ,m  ,r   ,m")))]
3399   "TARGET_64BIT"
3400   "@
3401    mov{l}\t{%1, %k0|%k0, %1}
3402    #
3403    movd\t{%1, %0|%0, %1}
3404    movd\t{%1, %0|%0, %1}
3405    %vmovd\t{%1, %0|%0, %1}
3406    %vmovd\t{%1, %0|%0, %1}"
3407   [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
3408    (set_attr "prefix" "orig,*,orig,orig,maybe_vex,maybe_vex")
3409    (set_attr "prefix_0f" "0,*,*,*,*,*")
3410    (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
3411
3412 (define_split
3413   [(set (match_operand:DI 0 "memory_operand" "")
3414         (zero_extend:DI (match_dup 0)))]
3415   "TARGET_64BIT"
3416   [(set (match_dup 4) (const_int 0))]
3417   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3418
3419 ;; %%% Kill me once multi-word ops are sane.
3420 (define_insn "zero_extendsidi2_1"
3421   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*x")
3422         (zero_extend:DI
3423          (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r   ,m  ,r   ,m")))
3424    (clobber (reg:CC FLAGS_REG))]
3425   "!TARGET_64BIT"
3426   "@
3427    #
3428    #
3429    #
3430    movd\t{%1, %0|%0, %1}
3431    movd\t{%1, %0|%0, %1}
3432    %vmovd\t{%1, %0|%0, %1}
3433    %vmovd\t{%1, %0|%0, %1}"
3434   [(set_attr "isa" "*,*,*,*,*,*,sse2")
3435    (set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")
3436    (set_attr "prefix" "*,*,*,orig,orig,maybe_vex,maybe_vex")
3437    (set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")])
3438
3439 (define_split
3440   [(set (match_operand:DI 0 "register_operand" "")
3441         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3442    (clobber (reg:CC FLAGS_REG))]
3443   "!TARGET_64BIT && reload_completed
3444    && true_regnum (operands[0]) == true_regnum (operands[1])"
3445   [(set (match_dup 4) (const_int 0))]
3446   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3447
3448 (define_split
3449   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3450         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3451    (clobber (reg:CC FLAGS_REG))]
3452   "!TARGET_64BIT && reload_completed
3453    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))"
3454   [(set (match_dup 3) (match_dup 1))
3455    (set (match_dup 4) (const_int 0))]
3456   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3457
3458 (define_insn "zero_extend<mode>di2"
3459   [(set (match_operand:DI 0 "register_operand" "=r")
3460         (zero_extend:DI
3461          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3462   "TARGET_64BIT"
3463   "movz{<imodesuffix>l|x}\t{%1, %k0|%k0, %1}"
3464   [(set_attr "type" "imovx")
3465    (set_attr "mode" "SI")])
3466
3467 (define_expand "zero_extendhisi2"
3468   [(set (match_operand:SI 0 "register_operand" "")
3469         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3470   ""
3471 {
3472   if (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3473     {
3474       operands[1] = force_reg (HImode, operands[1]);
3475       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3476       DONE;
3477     }
3478 })
3479
3480 (define_insn_and_split "zero_extendhisi2_and"
3481   [(set (match_operand:SI 0 "register_operand" "=r")
3482         (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3483    (clobber (reg:CC FLAGS_REG))]
3484   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3485   "#"
3486   "&& reload_completed"
3487   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3488               (clobber (reg:CC FLAGS_REG))])]
3489   ""
3490   [(set_attr "type" "alu1")
3491    (set_attr "mode" "SI")])
3492
3493 (define_insn "*zero_extendhisi2_movzwl"
3494   [(set (match_operand:SI 0 "register_operand" "=r")
3495         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3496   "!TARGET_ZERO_EXTEND_WITH_AND
3497    || optimize_function_for_size_p (cfun)"
3498   "movz{wl|x}\t{%1, %0|%0, %1}"
3499   [(set_attr "type" "imovx")
3500    (set_attr "mode" "SI")])
3501
3502 (define_expand "zero_extendqi<mode>2"
3503   [(parallel
3504     [(set (match_operand:SWI24 0 "register_operand" "")
3505           (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3506      (clobber (reg:CC FLAGS_REG))])])
3507
3508 (define_insn "*zero_extendqi<mode>2_and"
3509   [(set (match_operand:SWI24 0 "register_operand" "=r,?&q")
3510         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3511    (clobber (reg:CC FLAGS_REG))]
3512   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3513   "#"
3514   [(set_attr "type" "alu1")
3515    (set_attr "mode" "<MODE>")])
3516
3517 ;; When source and destination does not overlap, clear destination
3518 ;; first and then do the movb
3519 (define_split
3520   [(set (match_operand:SWI24 0 "register_operand" "")
3521         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3522    (clobber (reg:CC FLAGS_REG))]
3523   "reload_completed
3524    && (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3525    && ANY_QI_REG_P (operands[0])
3526    && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
3527    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3528   [(set (strict_low_part (match_dup 2)) (match_dup 1))]
3529 {
3530   operands[2] = gen_lowpart (QImode, operands[0]);
3531   ix86_expand_clear (operands[0]);
3532 })
3533
3534 (define_insn "*zero_extendqi<mode>2_movzbl_and"
3535   [(set (match_operand:SWI24 0 "register_operand" "=r,r")
3536         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3537    (clobber (reg:CC FLAGS_REG))]
3538   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun)"
3539   "#"
3540   [(set_attr "type" "imovx,alu1")
3541    (set_attr "mode" "<MODE>")])
3542
3543 ;; For the movzbl case strip only the clobber
3544 (define_split
3545   [(set (match_operand:SWI24 0 "register_operand" "")
3546         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3547    (clobber (reg:CC FLAGS_REG))]
3548   "reload_completed
3549    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
3550    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3551   [(set (match_dup 0)
3552         (zero_extend:SWI24 (match_dup 1)))])
3553
3554 ; zero extend to SImode to avoid partial register stalls
3555 (define_insn "*zero_extendqi<mode>2_movzbl"
3556   [(set (match_operand:SWI24 0 "register_operand" "=r")
3557         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3558   "reload_completed
3559    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
3560   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3561   [(set_attr "type" "imovx")
3562    (set_attr "mode" "SI")])
3563
3564 ;; Rest is handled by single and.
3565 (define_split
3566   [(set (match_operand:SWI24 0 "register_operand" "")
3567         (zero_extend:SWI24 (match_operand:QI 1 "register_operand" "")))
3568    (clobber (reg:CC FLAGS_REG))]
3569   "reload_completed
3570    && true_regnum (operands[0]) == true_regnum (operands[1])"
3571   [(parallel [(set (match_dup 0) (and:SWI24 (match_dup 0) (const_int 255)))
3572               (clobber (reg:CC FLAGS_REG))])])
3573 \f
3574 ;; Sign extension instructions
3575
3576 (define_expand "extendsidi2"
3577   [(set (match_operand:DI 0 "register_operand" "")
3578         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))]
3579   ""
3580 {
3581   if (!TARGET_64BIT)
3582     {
3583       emit_insn (gen_extendsidi2_1 (operands[0], operands[1]));
3584       DONE;
3585     }
3586 })
3587
3588 (define_insn "*extendsidi2_rex64"
3589   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3590         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3591   "TARGET_64BIT"
3592   "@
3593    {cltq|cdqe}
3594    movs{lq|x}\t{%1, %0|%0, %1}"
3595   [(set_attr "type" "imovx")
3596    (set_attr "mode" "DI")
3597    (set_attr "prefix_0f" "0")
3598    (set_attr "modrm" "0,1")])
3599
3600 (define_insn "extendsidi2_1"
3601   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3602         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3603    (clobber (reg:CC FLAGS_REG))
3604    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3605   "!TARGET_64BIT"
3606   "#")
3607
3608 ;; Extend to memory case when source register does die.
3609 (define_split
3610   [(set (match_operand:DI 0 "memory_operand" "")
3611         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3612    (clobber (reg:CC FLAGS_REG))
3613    (clobber (match_operand:SI 2 "register_operand" ""))]
3614   "(reload_completed
3615     && dead_or_set_p (insn, operands[1])
3616     && !reg_mentioned_p (operands[1], operands[0]))"
3617   [(set (match_dup 3) (match_dup 1))
3618    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3619               (clobber (reg:CC FLAGS_REG))])
3620    (set (match_dup 4) (match_dup 1))]
3621   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3622
3623 ;; Extend to memory case when source register does not die.
3624 (define_split
3625   [(set (match_operand:DI 0 "memory_operand" "")
3626         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3627    (clobber (reg:CC FLAGS_REG))
3628    (clobber (match_operand:SI 2 "register_operand" ""))]
3629   "reload_completed"
3630   [(const_int 0)]
3631 {
3632   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3633
3634   emit_move_insn (operands[3], operands[1]);
3635
3636   /* Generate a cltd if possible and doing so it profitable.  */
3637   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3638       && true_regnum (operands[1]) == AX_REG
3639       && true_regnum (operands[2]) == DX_REG)
3640     {
3641       emit_insn (gen_ashrsi3_cvt (operands[2], operands[1], GEN_INT (31)));
3642     }
3643   else
3644     {
3645       emit_move_insn (operands[2], operands[1]);
3646       emit_insn (gen_ashrsi3_cvt (operands[2], operands[2], GEN_INT (31)));
3647     }
3648   emit_move_insn (operands[4], operands[2]);
3649   DONE;
3650 })
3651
3652 ;; Extend to register case.  Optimize case where source and destination
3653 ;; registers match and cases where we can use cltd.
3654 (define_split
3655   [(set (match_operand:DI 0 "register_operand" "")
3656         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3657    (clobber (reg:CC FLAGS_REG))
3658    (clobber (match_scratch:SI 2 ""))]
3659   "reload_completed"
3660   [(const_int 0)]
3661 {
3662   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3663
3664   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3665     emit_move_insn (operands[3], operands[1]);
3666
3667   /* Generate a cltd if possible and doing so it profitable.  */
3668   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3669       && true_regnum (operands[3]) == AX_REG
3670       && true_regnum (operands[4]) == DX_REG)
3671     {
3672       emit_insn (gen_ashrsi3_cvt (operands[4], operands[3], GEN_INT (31)));
3673       DONE;
3674     }
3675
3676   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3677     emit_move_insn (operands[4], operands[1]);
3678
3679   emit_insn (gen_ashrsi3_cvt (operands[4], operands[4], GEN_INT (31)));
3680   DONE;
3681 })
3682
3683 (define_insn "extend<mode>di2"
3684   [(set (match_operand:DI 0 "register_operand" "=r")
3685         (sign_extend:DI
3686          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3687   "TARGET_64BIT"
3688   "movs{<imodesuffix>q|x}\t{%1, %0|%0, %1}"
3689   [(set_attr "type" "imovx")
3690    (set_attr "mode" "DI")])
3691
3692 (define_insn "extendhisi2"
3693   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3694         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3695   ""
3696 {
3697   switch (get_attr_prefix_0f (insn))
3698     {
3699     case 0:
3700       return "{cwtl|cwde}";
3701     default:
3702       return "movs{wl|x}\t{%1, %0|%0, %1}";
3703     }
3704 }
3705   [(set_attr "type" "imovx")
3706    (set_attr "mode" "SI")
3707    (set (attr "prefix_0f")
3708      ;; movsx is short decodable while cwtl is vector decoded.
3709      (if_then_else (and (eq_attr "cpu" "!k6")
3710                         (eq_attr "alternative" "0"))
3711         (const_string "0")
3712         (const_string "1")))
3713    (set (attr "modrm")
3714      (if_then_else (eq_attr "prefix_0f" "0")
3715         (const_string "0")
3716         (const_string "1")))])
3717
3718 (define_insn "*extendhisi2_zext"
3719   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3720         (zero_extend:DI
3721          (sign_extend:SI
3722           (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3723   "TARGET_64BIT"
3724 {
3725   switch (get_attr_prefix_0f (insn))
3726     {
3727     case 0:
3728       return "{cwtl|cwde}";
3729     default:
3730       return "movs{wl|x}\t{%1, %k0|%k0, %1}";
3731     }
3732 }
3733   [(set_attr "type" "imovx")
3734    (set_attr "mode" "SI")
3735    (set (attr "prefix_0f")
3736      ;; movsx is short decodable while cwtl is vector decoded.
3737      (if_then_else (and (eq_attr "cpu" "!k6")
3738                         (eq_attr "alternative" "0"))
3739         (const_string "0")
3740         (const_string "1")))
3741    (set (attr "modrm")
3742      (if_then_else (eq_attr "prefix_0f" "0")
3743         (const_string "0")
3744         (const_string "1")))])
3745
3746 (define_insn "extendqisi2"
3747   [(set (match_operand:SI 0 "register_operand" "=r")
3748         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3749   ""
3750   "movs{bl|x}\t{%1, %0|%0, %1}"
3751    [(set_attr "type" "imovx")
3752     (set_attr "mode" "SI")])
3753
3754 (define_insn "*extendqisi2_zext"
3755   [(set (match_operand:DI 0 "register_operand" "=r")
3756         (zero_extend:DI
3757           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3758   "TARGET_64BIT"
3759   "movs{bl|x}\t{%1, %k0|%k0, %1}"
3760    [(set_attr "type" "imovx")
3761     (set_attr "mode" "SI")])
3762
3763 (define_insn "extendqihi2"
3764   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3765         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3766   ""
3767 {
3768   switch (get_attr_prefix_0f (insn))
3769     {
3770     case 0:
3771       return "{cbtw|cbw}";
3772     default:
3773       return "movs{bw|x}\t{%1, %0|%0, %1}";
3774     }
3775 }
3776   [(set_attr "type" "imovx")
3777    (set_attr "mode" "HI")
3778    (set (attr "prefix_0f")
3779      ;; movsx is short decodable while cwtl is vector decoded.
3780      (if_then_else (and (eq_attr "cpu" "!k6")
3781                         (eq_attr "alternative" "0"))
3782         (const_string "0")
3783         (const_string "1")))
3784    (set (attr "modrm")
3785      (if_then_else (eq_attr "prefix_0f" "0")
3786         (const_string "0")
3787         (const_string "1")))])
3788 \f
3789 ;; Conversions between float and double.
3790
3791 ;; These are all no-ops in the model used for the 80387.
3792 ;; So just emit moves.
3793
3794 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3795 (define_split
3796   [(set (match_operand:DF 0 "push_operand" "")
3797         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3798   "reload_completed"
3799   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
3800    (set (mem:DF (reg:P SP_REG)) (float_extend:DF (match_dup 1)))])
3801
3802 (define_split
3803   [(set (match_operand:XF 0 "push_operand" "")
3804         (float_extend:XF (match_operand:MODEF 1 "fp_register_operand" "")))]
3805   "reload_completed"
3806   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3807    (set (mem:XF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
3808   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
3809
3810 (define_expand "extendsfdf2"
3811   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3812         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3813   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3814 {
3815   /* ??? Needed for compress_float_constant since all fp constants
3816      are TARGET_LEGITIMATE_CONSTANT_P.  */
3817   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3818     {
3819       if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
3820           && standard_80387_constant_p (operands[1]) > 0)
3821         {
3822           operands[1] = simplify_const_unary_operation
3823             (FLOAT_EXTEND, DFmode, operands[1], SFmode);
3824           emit_move_insn_1 (operands[0], operands[1]);
3825           DONE;
3826         }
3827       operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3828     }
3829 })
3830
3831 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
3832    cvtss2sd:
3833       unpcklps xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3834       cvtps2pd xmm2,xmm1
3835    We do the conversion post reload to avoid producing of 128bit spills
3836    that might lead to ICE on 32bit target.  The sequence unlikely combine
3837    anyway.  */
3838 (define_split
3839   [(set (match_operand:DF 0 "register_operand" "")
3840         (float_extend:DF
3841           (match_operand:SF 1 "nonimmediate_operand" "")))]
3842   "TARGET_USE_VECTOR_FP_CONVERTS
3843    && optimize_insn_for_speed_p ()
3844    && reload_completed && SSE_REG_P (operands[0])"
3845    [(set (match_dup 2)
3846          (float_extend:V2DF
3847            (vec_select:V2SF
3848              (match_dup 3)
3849              (parallel [(const_int 0) (const_int 1)]))))]
3850 {
3851   operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
3852   operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
3853   /* Use movss for loading from memory, unpcklps reg, reg for registers.
3854      Try to avoid move when unpacking can be done in source.  */
3855   if (REG_P (operands[1]))
3856     {
3857       /* If it is unsafe to overwrite upper half of source, we need
3858          to move to destination and unpack there.  */
3859       if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
3860            || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
3861           && true_regnum (operands[0]) != true_regnum (operands[1]))
3862         {
3863           rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
3864           emit_move_insn (tmp, operands[1]);
3865         }
3866       else
3867         operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
3868       emit_insn (gen_vec_interleave_lowv4sf (operands[3], operands[3],
3869                                              operands[3]));
3870     }
3871   else
3872     emit_insn (gen_vec_setv4sf_0 (operands[3],
3873                                   CONST0_RTX (V4SFmode), operands[1]));
3874 })
3875
3876 (define_insn "*extendsfdf2_mixed"
3877   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
3878         (float_extend:DF
3879           (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
3880   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3881 {
3882   switch (which_alternative)
3883     {
3884     case 0:
3885     case 1:
3886       return output_387_reg_move (insn, operands);
3887
3888     case 2:
3889       return "%vcvtss2sd\t{%1, %d0|%d0, %1}";
3890
3891     default:
3892       gcc_unreachable ();
3893     }
3894 }
3895   [(set_attr "type" "fmov,fmov,ssecvt")
3896    (set_attr "prefix" "orig,orig,maybe_vex")
3897    (set_attr "mode" "SF,XF,DF")])
3898
3899 (define_insn "*extendsfdf2_sse"
3900   [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
3901         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
3902   "TARGET_SSE2 && TARGET_SSE_MATH"
3903   "%vcvtss2sd\t{%1, %d0|%d0, %1}"
3904   [(set_attr "type" "ssecvt")
3905    (set_attr "prefix" "maybe_vex")
3906    (set_attr "mode" "DF")])
3907
3908 (define_insn "*extendsfdf2_i387"
3909   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3910         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3911   "TARGET_80387"
3912   "* return output_387_reg_move (insn, operands);"
3913   [(set_attr "type" "fmov")
3914    (set_attr "mode" "SF,XF")])
3915
3916 (define_expand "extend<mode>xf2"
3917   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3918         (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
3919   "TARGET_80387"
3920 {
3921   /* ??? Needed for compress_float_constant since all fp constants
3922      are TARGET_LEGITIMATE_CONSTANT_P.  */
3923   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3924     {
3925       if (standard_80387_constant_p (operands[1]) > 0)
3926         {
3927           operands[1] = simplify_const_unary_operation
3928             (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
3929           emit_move_insn_1 (operands[0], operands[1]);
3930           DONE;
3931         }
3932       operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
3933     }
3934 })
3935
3936 (define_insn "*extend<mode>xf2_i387"
3937   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3938         (float_extend:XF
3939           (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
3940   "TARGET_80387"
3941   "* return output_387_reg_move (insn, operands);"
3942   [(set_attr "type" "fmov")
3943    (set_attr "mode" "<MODE>,XF")])
3944
3945 ;; %%% This seems bad bad news.
3946 ;; This cannot output into an f-reg because there is no way to be sure
3947 ;; of truncating in that case.  Otherwise this is just like a simple move
3948 ;; insn.  So we pretend we can output to a reg in order to get better
3949 ;; register preferencing, but we really use a stack slot.
3950
3951 ;; Conversion from DFmode to SFmode.
3952
3953 (define_expand "truncdfsf2"
3954   [(set (match_operand:SF 0 "nonimmediate_operand" "")
3955         (float_truncate:SF
3956           (match_operand:DF 1 "nonimmediate_operand" "")))]
3957   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3958 {
3959   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3960     ;
3961   else if (flag_unsafe_math_optimizations)
3962     ;
3963   else
3964     {
3965       rtx temp = assign_386_stack_local (SFmode, SLOT_TEMP);
3966       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3967       DONE;
3968     }
3969 })
3970
3971 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
3972    cvtsd2ss:
3973       unpcklpd xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3974       cvtpd2ps xmm2,xmm1
3975    We do the conversion post reload to avoid producing of 128bit spills
3976    that might lead to ICE on 32bit target.  The sequence unlikely combine
3977    anyway.  */
3978 (define_split
3979   [(set (match_operand:SF 0 "register_operand" "")
3980         (float_truncate:SF
3981           (match_operand:DF 1 "nonimmediate_operand" "")))]
3982   "TARGET_USE_VECTOR_FP_CONVERTS
3983    && optimize_insn_for_speed_p ()
3984    && reload_completed && SSE_REG_P (operands[0])"
3985    [(set (match_dup 2)
3986          (vec_concat:V4SF
3987            (float_truncate:V2SF
3988              (match_dup 4))
3989            (match_dup 3)))]
3990 {
3991   operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
3992   operands[3] = CONST0_RTX (V2SFmode);
3993   operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
3994   /* Use movsd for loading from memory, unpcklpd for registers.
3995      Try to avoid move when unpacking can be done in source, or SSE3
3996      movddup is available.  */
3997   if (REG_P (operands[1]))
3998     {
3999       if (!TARGET_SSE3
4000           && true_regnum (operands[0]) != true_regnum (operands[1])
4001           && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4002               || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
4003         {
4004           rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
4005           emit_move_insn (tmp, operands[1]);
4006           operands[1] = tmp;
4007         }
4008       else if (!TARGET_SSE3)
4009         operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4010       emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4011     }
4012   else
4013     emit_insn (gen_sse2_loadlpd (operands[4],
4014                                  CONST0_RTX (V2DFmode), operands[1]));
4015 })
4016
4017 (define_expand "truncdfsf2_with_temp"
4018   [(parallel [(set (match_operand:SF 0 "" "")
4019                    (float_truncate:SF (match_operand:DF 1 "" "")))
4020               (clobber (match_operand:SF 2 "" ""))])])
4021
4022 (define_insn "*truncdfsf_fast_mixed"
4023   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm,x")
4024         (float_truncate:SF
4025           (match_operand:DF 1 "nonimmediate_operand" "f  ,xm")))]
4026   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4027 {
4028   switch (which_alternative)
4029     {
4030     case 0:
4031       return output_387_reg_move (insn, operands);
4032     case 1:
4033       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4034     default:
4035       gcc_unreachable ();
4036     }
4037 }
4038   [(set_attr "type" "fmov,ssecvt")
4039    (set_attr "prefix" "orig,maybe_vex")
4040    (set_attr "mode" "SF")])
4041
4042 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4043 ;; because nothing we do here is unsafe.
4044 (define_insn "*truncdfsf_fast_sse"
4045   [(set (match_operand:SF 0 "nonimmediate_operand"   "=x")
4046         (float_truncate:SF
4047           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4048   "TARGET_SSE2 && TARGET_SSE_MATH"
4049   "%vcvtsd2ss\t{%1, %d0|%d0, %1}"
4050   [(set_attr "type" "ssecvt")
4051    (set_attr "prefix" "maybe_vex")
4052    (set_attr "mode" "SF")])
4053
4054 (define_insn "*truncdfsf_fast_i387"
4055   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
4056         (float_truncate:SF
4057           (match_operand:DF 1 "nonimmediate_operand" "f")))]
4058   "TARGET_80387 && flag_unsafe_math_optimizations"
4059   "* return output_387_reg_move (insn, operands);"
4060   [(set_attr "type" "fmov")
4061    (set_attr "mode" "SF")])
4062
4063 (define_insn "*truncdfsf_mixed"
4064   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,x ,?f,?x,?*r")
4065         (float_truncate:SF
4066           (match_operand:DF 1 "nonimmediate_operand" "f ,xm,f ,f ,f")))
4067    (clobber (match_operand:SF 2 "memory_operand"     "=X,X ,m ,m ,m"))]
4068   "TARGET_MIX_SSE_I387"
4069 {
4070   switch (which_alternative)
4071     {
4072     case 0:
4073       return output_387_reg_move (insn, operands);
4074     case 1:
4075       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4076
4077     default:
4078       return "#";
4079     }
4080 }
4081   [(set_attr "isa" "*,sse2,*,*,*")
4082    (set_attr "type" "fmov,ssecvt,multi,multi,multi")
4083    (set_attr "unit" "*,*,i387,i387,i387")
4084    (set_attr "prefix" "orig,maybe_vex,orig,orig,orig")
4085    (set_attr "mode" "SF")])
4086
4087 (define_insn "*truncdfsf_i387"
4088   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?f,?x,?*r")
4089         (float_truncate:SF
4090           (match_operand:DF 1 "nonimmediate_operand" "f ,f ,f ,f")))
4091    (clobber (match_operand:SF 2 "memory_operand"     "=X,m ,m ,m"))]
4092   "TARGET_80387"
4093 {
4094   switch (which_alternative)
4095     {
4096     case 0:
4097       return output_387_reg_move (insn, operands);
4098
4099     default:
4100       return "#";
4101     }
4102 }
4103   [(set_attr "type" "fmov,multi,multi,multi")
4104    (set_attr "unit" "*,i387,i387,i387")
4105    (set_attr "mode" "SF")])
4106
4107 (define_insn "*truncdfsf2_i387_1"
4108   [(set (match_operand:SF 0 "memory_operand" "=m")
4109         (float_truncate:SF
4110           (match_operand:DF 1 "register_operand" "f")))]
4111   "TARGET_80387
4112    && !(TARGET_SSE2 && TARGET_SSE_MATH)
4113    && !TARGET_MIX_SSE_I387"
4114   "* return output_387_reg_move (insn, operands);"
4115   [(set_attr "type" "fmov")
4116    (set_attr "mode" "SF")])
4117
4118 (define_split
4119   [(set (match_operand:SF 0 "register_operand" "")
4120         (float_truncate:SF
4121          (match_operand:DF 1 "fp_register_operand" "")))
4122    (clobber (match_operand 2 "" ""))]
4123   "reload_completed"
4124   [(set (match_dup 2) (match_dup 1))
4125    (set (match_dup 0) (match_dup 2))]
4126   "operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));")
4127
4128 ;; Conversion from XFmode to {SF,DF}mode
4129
4130 (define_expand "truncxf<mode>2"
4131   [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4132                    (float_truncate:MODEF
4133                      (match_operand:XF 1 "register_operand" "")))
4134               (clobber (match_dup 2))])]
4135   "TARGET_80387"
4136 {
4137   if (flag_unsafe_math_optimizations)
4138     {
4139       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4140       emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4141       if (reg != operands[0])
4142         emit_move_insn (operands[0], reg);
4143       DONE;
4144     }
4145   else
4146     operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4147 })
4148
4149 (define_insn "*truncxfsf2_mixed"
4150   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4151         (float_truncate:SF
4152           (match_operand:XF 1 "register_operand"   "f ,f ,f ,f")))
4153    (clobber (match_operand:SF 2 "memory_operand"   "=X,m ,m ,m"))]
4154   "TARGET_80387"
4155 {
4156   gcc_assert (!which_alternative);
4157   return output_387_reg_move (insn, operands);
4158 }
4159   [(set_attr "type" "fmov,multi,multi,multi")
4160    (set_attr "unit" "*,i387,i387,i387")
4161    (set_attr "mode" "SF")])
4162
4163 (define_insn "*truncxfdf2_mixed"
4164   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4165         (float_truncate:DF
4166           (match_operand:XF 1 "register_operand"   "f ,f ,f  ,f")))
4167    (clobber (match_operand:DF 2 "memory_operand"   "=X,m ,m  ,m"))]
4168   "TARGET_80387"
4169 {
4170   gcc_assert (!which_alternative);
4171   return output_387_reg_move (insn, operands);
4172 }
4173   [(set_attr "isa" "*,*,sse2,*")
4174    (set_attr "type" "fmov,multi,multi,multi")
4175    (set_attr "unit" "*,i387,i387,i387")
4176    (set_attr "mode" "DF")])
4177
4178 (define_insn "truncxf<mode>2_i387_noop"
4179   [(set (match_operand:MODEF 0 "register_operand" "=f")
4180         (float_truncate:MODEF
4181           (match_operand:XF 1 "register_operand" "f")))]
4182   "TARGET_80387 && flag_unsafe_math_optimizations"
4183   "* return output_387_reg_move (insn, operands);"
4184   [(set_attr "type" "fmov")
4185    (set_attr "mode" "<MODE>")])
4186
4187 (define_insn "*truncxf<mode>2_i387"
4188   [(set (match_operand:MODEF 0 "memory_operand" "=m")
4189         (float_truncate:MODEF
4190           (match_operand:XF 1 "register_operand" "f")))]
4191   "TARGET_80387"
4192   "* return output_387_reg_move (insn, operands);"
4193   [(set_attr "type" "fmov")
4194    (set_attr "mode" "<MODE>")])
4195
4196 (define_split
4197   [(set (match_operand:MODEF 0 "register_operand" "")
4198         (float_truncate:MODEF
4199           (match_operand:XF 1 "register_operand" "")))
4200    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4201   "TARGET_80387 && reload_completed"
4202   [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4203    (set (match_dup 0) (match_dup 2))])
4204
4205 (define_split
4206   [(set (match_operand:MODEF 0 "memory_operand" "")
4207         (float_truncate:MODEF
4208           (match_operand:XF 1 "register_operand" "")))
4209    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4210   "TARGET_80387"
4211   [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))])
4212 \f
4213 ;; Signed conversion to DImode.
4214
4215 (define_expand "fix_truncxfdi2"
4216   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4217                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4218               (clobber (reg:CC FLAGS_REG))])]
4219   "TARGET_80387"
4220 {
4221   if (TARGET_FISTTP)
4222    {
4223      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4224      DONE;
4225    }
4226 })
4227
4228 (define_expand "fix_trunc<mode>di2"
4229   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4230                    (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4231               (clobber (reg:CC FLAGS_REG))])]
4232   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4233 {
4234   if (TARGET_FISTTP
4235       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4236    {
4237      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4238      DONE;
4239    }
4240   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4241    {
4242      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4243      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4244      if (out != operands[0])
4245         emit_move_insn (operands[0], out);
4246      DONE;
4247    }
4248 })
4249
4250 ;; Signed conversion to SImode.
4251
4252 (define_expand "fix_truncxfsi2"
4253   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4254                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4255               (clobber (reg:CC FLAGS_REG))])]
4256   "TARGET_80387"
4257 {
4258   if (TARGET_FISTTP)
4259    {
4260      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4261      DONE;
4262    }
4263 })
4264
4265 (define_expand "fix_trunc<mode>si2"
4266   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4267                    (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4268               (clobber (reg:CC FLAGS_REG))])]
4269   "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4270 {
4271   if (TARGET_FISTTP
4272       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4273    {
4274      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4275      DONE;
4276    }
4277   if (SSE_FLOAT_MODE_P (<MODE>mode))
4278    {
4279      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4280      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4281      if (out != operands[0])
4282         emit_move_insn (operands[0], out);
4283      DONE;
4284    }
4285 })
4286
4287 ;; Signed conversion to HImode.
4288
4289 (define_expand "fix_trunc<mode>hi2"
4290   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4291                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4292               (clobber (reg:CC FLAGS_REG))])]
4293   "TARGET_80387
4294    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4295 {
4296   if (TARGET_FISTTP)
4297    {
4298      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4299      DONE;
4300    }
4301 })
4302
4303 ;; Unsigned conversion to SImode.
4304
4305 (define_expand "fixuns_trunc<mode>si2"
4306   [(parallel
4307     [(set (match_operand:SI 0 "register_operand" "")
4308           (unsigned_fix:SI
4309             (match_operand:MODEF 1 "nonimmediate_operand" "")))
4310      (use (match_dup 2))
4311      (clobber (match_scratch:<ssevecmode> 3 ""))
4312      (clobber (match_scratch:<ssevecmode> 4 ""))])]
4313   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4314 {
4315   enum machine_mode mode = <MODE>mode;
4316   enum machine_mode vecmode = <ssevecmode>mode;
4317   REAL_VALUE_TYPE TWO31r;
4318   rtx two31;
4319
4320   if (optimize_insn_for_size_p ())
4321     FAIL;
4322
4323   real_ldexp (&TWO31r, &dconst1, 31);
4324   two31 = const_double_from_real_value (TWO31r, mode);
4325   two31 = ix86_build_const_vector (vecmode, true, two31);
4326   operands[2] = force_reg (vecmode, two31);
4327 })
4328
4329 (define_insn_and_split "*fixuns_trunc<mode>_1"
4330   [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4331         (unsigned_fix:SI
4332           (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4333    (use (match_operand:<ssevecmode> 4  "nonimmediate_operand" "m,x"))
4334    (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4335    (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4336   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
4337    && optimize_function_for_speed_p (cfun)"
4338   "#"
4339   "&& reload_completed"
4340   [(const_int 0)]
4341 {
4342   ix86_split_convert_uns_si_sse (operands);
4343   DONE;
4344 })
4345
4346 ;; Unsigned conversion to HImode.
4347 ;; Without these patterns, we'll try the unsigned SI conversion which
4348 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4349
4350 (define_expand "fixuns_trunc<mode>hi2"
4351   [(set (match_dup 2)
4352         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4353    (set (match_operand:HI 0 "nonimmediate_operand" "")
4354         (subreg:HI (match_dup 2) 0))]
4355   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4356   "operands[2] = gen_reg_rtx (SImode);")
4357
4358 ;; When SSE is available, it is always faster to use it!
4359 (define_insn "fix_trunc<mode>di_sse"
4360   [(set (match_operand:DI 0 "register_operand" "=r,r")
4361         (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4362   "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4363    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4364   "%vcvtt<ssemodesuffix>2si{q}\t{%1, %0|%0, %1}"
4365   [(set_attr "type" "sseicvt")
4366    (set_attr "prefix" "maybe_vex")
4367    (set_attr "prefix_rex" "1")
4368    (set_attr "mode" "<MODE>")
4369    (set_attr "athlon_decode" "double,vector")
4370    (set_attr "amdfam10_decode" "double,double")
4371    (set_attr "bdver1_decode" "double,double")])
4372
4373 (define_insn "fix_trunc<mode>si_sse"
4374   [(set (match_operand:SI 0 "register_operand" "=r,r")
4375         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4376   "SSE_FLOAT_MODE_P (<MODE>mode)
4377    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4378   "%vcvtt<ssemodesuffix>2si\t{%1, %0|%0, %1}"
4379   [(set_attr "type" "sseicvt")
4380    (set_attr "prefix" "maybe_vex")
4381    (set_attr "mode" "<MODE>")
4382    (set_attr "athlon_decode" "double,vector")
4383    (set_attr "amdfam10_decode" "double,double")
4384    (set_attr "bdver1_decode" "double,double")])
4385
4386 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4387 (define_peephole2
4388   [(set (match_operand:MODEF 0 "register_operand" "")
4389         (match_operand:MODEF 1 "memory_operand" ""))
4390    (set (match_operand:SWI48x 2 "register_operand" "")
4391         (fix:SWI48x (match_dup 0)))]
4392   "TARGET_SHORTEN_X87_SSE
4393    && !(TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ())
4394    && peep2_reg_dead_p (2, operands[0])"
4395   [(set (match_dup 2) (fix:SWI48x (match_dup 1)))])
4396
4397 ;; Avoid vector decoded forms of the instruction.
4398 (define_peephole2
4399   [(match_scratch:DF 2 "x")
4400    (set (match_operand:SWI48x 0 "register_operand" "")
4401         (fix:SWI48x (match_operand:DF 1 "memory_operand" "")))]
4402   "TARGET_SSE2 && TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4403   [(set (match_dup 2) (match_dup 1))
4404    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4405
4406 (define_peephole2
4407   [(match_scratch:SF 2 "x")
4408    (set (match_operand:SWI48x 0 "register_operand" "")
4409         (fix:SWI48x (match_operand:SF 1 "memory_operand" "")))]
4410   "TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4411   [(set (match_dup 2) (match_dup 1))
4412    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4413
4414 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4415   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4416         (fix:SWI248x (match_operand 1 "register_operand" "")))]
4417   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4418    && TARGET_FISTTP
4419    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4420          && (TARGET_64BIT || <MODE>mode != DImode))
4421         && TARGET_SSE_MATH)
4422    && can_create_pseudo_p ()"
4423   "#"
4424   "&& 1"
4425   [(const_int 0)]
4426 {
4427   if (memory_operand (operands[0], VOIDmode))
4428     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4429   else
4430     {
4431       operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4432       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4433                                                             operands[1],
4434                                                             operands[2]));
4435     }
4436   DONE;
4437 }
4438   [(set_attr "type" "fisttp")
4439    (set_attr "mode" "<MODE>")])
4440
4441 (define_insn "fix_trunc<mode>_i387_fisttp"
4442   [(set (match_operand:SWI248x 0 "memory_operand" "=m")
4443         (fix:SWI248x (match_operand 1 "register_operand" "f")))
4444    (clobber (match_scratch:XF 2 "=&1f"))]
4445   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4446    && TARGET_FISTTP
4447    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4448          && (TARGET_64BIT || <MODE>mode != DImode))
4449         && TARGET_SSE_MATH)"
4450   "* return output_fix_trunc (insn, operands, true);"
4451   [(set_attr "type" "fisttp")
4452    (set_attr "mode" "<MODE>")])
4453
4454 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4455   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "=m,?r")
4456         (fix:SWI248x (match_operand 1 "register_operand" "f,f")))
4457    (clobber (match_operand:SWI248x 2 "memory_operand" "=X,m"))
4458    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4459   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4460    && TARGET_FISTTP
4461    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4462         && (TARGET_64BIT || <MODE>mode != DImode))
4463         && TARGET_SSE_MATH)"
4464   "#"
4465   [(set_attr "type" "fisttp")
4466    (set_attr "mode" "<MODE>")])
4467
4468 (define_split
4469   [(set (match_operand:SWI248x 0 "register_operand" "")
4470         (fix:SWI248x (match_operand 1 "register_operand" "")))
4471    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4472    (clobber (match_scratch 3 ""))]
4473   "reload_completed"
4474   [(parallel [(set (match_dup 2) (fix:SWI248x (match_dup 1)))
4475               (clobber (match_dup 3))])
4476    (set (match_dup 0) (match_dup 2))])
4477
4478 (define_split
4479   [(set (match_operand:SWI248x 0 "memory_operand" "")
4480         (fix:SWI248x (match_operand 1 "register_operand" "")))
4481    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4482    (clobber (match_scratch 3 ""))]
4483   "reload_completed"
4484   [(parallel [(set (match_dup 0) (fix:SWI248x (match_dup 1)))
4485               (clobber (match_dup 3))])])
4486
4487 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4488 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4489 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4490 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4491 ;; function in i386.c.
4492 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4493   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4494         (fix:SWI248x (match_operand 1 "register_operand" "")))
4495    (clobber (reg:CC FLAGS_REG))]
4496   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4497    && !TARGET_FISTTP
4498    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4499          && (TARGET_64BIT || <MODE>mode != DImode))
4500    && can_create_pseudo_p ()"
4501   "#"
4502   "&& 1"
4503   [(const_int 0)]
4504 {
4505   ix86_optimize_mode_switching[I387_TRUNC] = 1;
4506
4507   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4508   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4509   if (memory_operand (operands[0], VOIDmode))
4510     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4511                                          operands[2], operands[3]));
4512   else
4513     {
4514       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4515       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4516                                                      operands[2], operands[3],
4517                                                      operands[4]));
4518     }
4519   DONE;
4520 }
4521   [(set_attr "type" "fistp")
4522    (set_attr "i387_cw" "trunc")
4523    (set_attr "mode" "<MODE>")])
4524
4525 (define_insn "fix_truncdi_i387"
4526   [(set (match_operand:DI 0 "memory_operand" "=m")
4527         (fix:DI (match_operand 1 "register_operand" "f")))
4528    (use (match_operand:HI 2 "memory_operand" "m"))
4529    (use (match_operand:HI 3 "memory_operand" "m"))
4530    (clobber (match_scratch:XF 4 "=&1f"))]
4531   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4532    && !TARGET_FISTTP
4533    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4534   "* return output_fix_trunc (insn, operands, false);"
4535   [(set_attr "type" "fistp")
4536    (set_attr "i387_cw" "trunc")
4537    (set_attr "mode" "DI")])
4538
4539 (define_insn "fix_truncdi_i387_with_temp"
4540   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4541         (fix:DI (match_operand 1 "register_operand" "f,f")))
4542    (use (match_operand:HI 2 "memory_operand" "m,m"))
4543    (use (match_operand:HI 3 "memory_operand" "m,m"))
4544    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
4545    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4546   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4547    && !TARGET_FISTTP
4548    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4549   "#"
4550   [(set_attr "type" "fistp")
4551    (set_attr "i387_cw" "trunc")
4552    (set_attr "mode" "DI")])
4553
4554 (define_split
4555   [(set (match_operand:DI 0 "register_operand" "")
4556         (fix:DI (match_operand 1 "register_operand" "")))
4557    (use (match_operand:HI 2 "memory_operand" ""))
4558    (use (match_operand:HI 3 "memory_operand" ""))
4559    (clobber (match_operand:DI 4 "memory_operand" ""))
4560    (clobber (match_scratch 5 ""))]
4561   "reload_completed"
4562   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4563               (use (match_dup 2))
4564               (use (match_dup 3))
4565               (clobber (match_dup 5))])
4566    (set (match_dup 0) (match_dup 4))])
4567
4568 (define_split
4569   [(set (match_operand:DI 0 "memory_operand" "")
4570         (fix:DI (match_operand 1 "register_operand" "")))
4571    (use (match_operand:HI 2 "memory_operand" ""))
4572    (use (match_operand:HI 3 "memory_operand" ""))
4573    (clobber (match_operand:DI 4 "memory_operand" ""))
4574    (clobber (match_scratch 5 ""))]
4575   "reload_completed"
4576   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4577               (use (match_dup 2))
4578               (use (match_dup 3))
4579               (clobber (match_dup 5))])])
4580
4581 (define_insn "fix_trunc<mode>_i387"
4582   [(set (match_operand:SWI24 0 "memory_operand" "=m")
4583         (fix:SWI24 (match_operand 1 "register_operand" "f")))
4584    (use (match_operand:HI 2 "memory_operand" "m"))
4585    (use (match_operand:HI 3 "memory_operand" "m"))]
4586   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4587    && !TARGET_FISTTP
4588    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4589   "* return output_fix_trunc (insn, operands, false);"
4590   [(set_attr "type" "fistp")
4591    (set_attr "i387_cw" "trunc")
4592    (set_attr "mode" "<MODE>")])
4593
4594 (define_insn "fix_trunc<mode>_i387_with_temp"
4595   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
4596         (fix:SWI24 (match_operand 1 "register_operand" "f,f")))
4597    (use (match_operand:HI 2 "memory_operand" "m,m"))
4598    (use (match_operand:HI 3 "memory_operand" "m,m"))
4599    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
4600   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4601    && !TARGET_FISTTP
4602    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4603   "#"
4604   [(set_attr "type" "fistp")
4605    (set_attr "i387_cw" "trunc")
4606    (set_attr "mode" "<MODE>")])
4607
4608 (define_split
4609   [(set (match_operand:SWI24 0 "register_operand" "")
4610         (fix:SWI24 (match_operand 1 "register_operand" "")))
4611    (use (match_operand:HI 2 "memory_operand" ""))
4612    (use (match_operand:HI 3 "memory_operand" ""))
4613    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4614   "reload_completed"
4615   [(parallel [(set (match_dup 4) (fix:SWI24 (match_dup 1)))
4616               (use (match_dup 2))
4617               (use (match_dup 3))])
4618    (set (match_dup 0) (match_dup 4))])
4619
4620 (define_split
4621   [(set (match_operand:SWI24 0 "memory_operand" "")
4622         (fix:SWI24 (match_operand 1 "register_operand" "")))
4623    (use (match_operand:HI 2 "memory_operand" ""))
4624    (use (match_operand:HI 3 "memory_operand" ""))
4625    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4626   "reload_completed"
4627   [(parallel [(set (match_dup 0) (fix:SWI24 (match_dup 1)))
4628               (use (match_dup 2))
4629               (use (match_dup 3))])])
4630
4631 (define_insn "x86_fnstcw_1"
4632   [(set (match_operand:HI 0 "memory_operand" "=m")
4633         (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
4634   "TARGET_80387"
4635   "fnstcw\t%0"
4636   [(set (attr "length")
4637         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4638    (set_attr "mode" "HI")
4639    (set_attr "unit" "i387")
4640    (set_attr "bdver1_decode" "vector")])
4641
4642 (define_insn "x86_fldcw_1"
4643   [(set (reg:HI FPCR_REG)
4644         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4645   "TARGET_80387"
4646   "fldcw\t%0"
4647   [(set (attr "length")
4648         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4649    (set_attr "mode" "HI")
4650    (set_attr "unit" "i387")
4651    (set_attr "athlon_decode" "vector")
4652    (set_attr "amdfam10_decode" "vector")
4653    (set_attr "bdver1_decode" "vector")])
4654 \f
4655 ;; Conversion between fixed point and floating point.
4656
4657 ;; Even though we only accept memory inputs, the backend _really_
4658 ;; wants to be able to do this between registers.
4659
4660 (define_expand "floathi<mode>2"
4661   [(set (match_operand:X87MODEF 0 "register_operand" "")
4662         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
4663   "TARGET_80387
4664    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4665        || TARGET_MIX_SSE_I387)")
4666
4667 ;; Pre-reload splitter to add memory clobber to the pattern.
4668 (define_insn_and_split "*floathi<mode>2_1"
4669   [(set (match_operand:X87MODEF 0 "register_operand" "")
4670         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))]
4671   "TARGET_80387
4672    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4673        || TARGET_MIX_SSE_I387)
4674    && can_create_pseudo_p ()"
4675   "#"
4676   "&& 1"
4677   [(parallel [(set (match_dup 0)
4678               (float:X87MODEF (match_dup 1)))
4679    (clobber (match_dup 2))])]
4680   "operands[2] = assign_386_stack_local (HImode, SLOT_TEMP);")
4681
4682 (define_insn "*floathi<mode>2_i387_with_temp"
4683   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
4684         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))
4685   (clobber (match_operand:HI 2 "memory_operand" "=X,m"))]
4686   "TARGET_80387
4687    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4688        || TARGET_MIX_SSE_I387)"
4689   "#"
4690   [(set_attr "type" "fmov,multi")
4691    (set_attr "mode" "<MODE>")
4692    (set_attr "unit" "*,i387")
4693    (set_attr "fp_int_src" "true")])
4694
4695 (define_insn "*floathi<mode>2_i387"
4696   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
4697         (float:X87MODEF (match_operand:HI 1 "memory_operand" "m")))]
4698   "TARGET_80387
4699    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4700        || TARGET_MIX_SSE_I387)"
4701   "fild%Z1\t%1"
4702   [(set_attr "type" "fmov")
4703    (set_attr "mode" "<MODE>")
4704    (set_attr "fp_int_src" "true")])
4705
4706 (define_split
4707   [(set (match_operand:X87MODEF 0 "register_operand" "")
4708         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))
4709    (clobber (match_operand:HI 2 "memory_operand" ""))]
4710   "TARGET_80387
4711    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4712        || TARGET_MIX_SSE_I387)
4713    && reload_completed"
4714   [(set (match_dup 2) (match_dup 1))
4715    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
4716
4717 (define_split
4718   [(set (match_operand:X87MODEF 0 "register_operand" "")
4719         (float:X87MODEF (match_operand:HI 1 "memory_operand" "")))
4720    (clobber (match_operand:HI 2 "memory_operand" ""))]
4721    "TARGET_80387
4722     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4723         || TARGET_MIX_SSE_I387)
4724     && reload_completed"
4725   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
4726
4727 (define_expand "float<SWI48x:mode><X87MODEF:mode>2"
4728   [(set (match_operand:X87MODEF 0 "register_operand" "")
4729         (float:X87MODEF
4730           (match_operand:SWI48x 1 "nonimmediate_operand" "")))]
4731   "TARGET_80387
4732    || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4733        && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)"
4734 {
4735   if (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4736         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4737       && !X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode))
4738     {
4739       rtx reg = gen_reg_rtx (XFmode);
4740       rtx (*insn)(rtx, rtx);
4741
4742       emit_insn (gen_float<SWI48x:mode>xf2 (reg, operands[1]));
4743
4744       if (<X87MODEF:MODE>mode == SFmode)
4745         insn = gen_truncxfsf2;
4746       else if (<X87MODEF:MODE>mode == DFmode)
4747         insn = gen_truncxfdf2;
4748       else
4749         gcc_unreachable ();
4750
4751       emit_insn (insn (operands[0], reg));
4752       DONE;
4753     }
4754 })
4755
4756 ;; Pre-reload splitter to add memory clobber to the pattern.
4757 (define_insn_and_split "*float<SWI48x:mode><X87MODEF:mode>2_1"
4758   [(set (match_operand:X87MODEF 0 "register_operand" "")
4759         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))]
4760   "((TARGET_80387
4761      && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
4762      && (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4763            && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4764          || TARGET_MIX_SSE_I387))
4765     || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4766         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
4767         && ((<SWI48x:MODE>mode == SImode
4768              && TARGET_SSE2 && TARGET_USE_VECTOR_CONVERTS
4769              && optimize_function_for_speed_p (cfun)
4770              && flag_trapping_math)
4771             || !(TARGET_INTER_UNIT_CONVERSIONS
4772                  || optimize_function_for_size_p (cfun)))))
4773    && can_create_pseudo_p ()"
4774   "#"
4775   "&& 1"
4776   [(parallel [(set (match_dup 0) (float:X87MODEF (match_dup 1)))
4777               (clobber (match_dup 2))])]
4778 {
4779   operands[2] = assign_386_stack_local (<SWI48x:MODE>mode, SLOT_TEMP);
4780
4781   /* Avoid store forwarding (partial memory) stall penalty
4782      by passing DImode value through XMM registers.  */
4783   if (<SWI48x:MODE>mode == DImode && !TARGET_64BIT
4784       && TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
4785       && optimize_function_for_speed_p (cfun))
4786     {
4787       emit_insn (gen_floatdi<X87MODEF:mode>2_i387_with_xmm (operands[0],
4788                                                             operands[1],
4789                                                             operands[2]));
4790       DONE;
4791     }
4792 })
4793
4794 (define_insn "*floatsi<mode>2_vector_mixed_with_temp"
4795   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x,x")
4796         (float:MODEF
4797           (match_operand:SI 1 "nonimmediate_operand" "m,?r,r,m,!x")))
4798    (clobber (match_operand:SI 2 "memory_operand" "=X,m,m,X,m"))]
4799   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4800    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4801   "#"
4802   [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
4803    (set_attr "mode" "<MODE>,<MODE>,<MODE>,<MODE>,<ssevecmode>")
4804    (set_attr "unit" "*,i387,*,*,*")
4805    (set_attr "athlon_decode" "*,*,double,direct,double")
4806    (set_attr "amdfam10_decode" "*,*,vector,double,double")
4807    (set_attr "bdver1_decode" "*,*,double,direct,double")
4808    (set_attr "fp_int_src" "true")])
4809
4810 (define_insn "*floatsi<mode>2_vector_mixed"
4811   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4812         (float:MODEF (match_operand:SI 1 "memory_operand" "m,m")))]
4813   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4814    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4815   "@
4816    fild%Z1\t%1
4817    #"
4818   [(set_attr "type" "fmov,sseicvt")
4819    (set_attr "mode" "<MODE>,<ssevecmode>")
4820    (set_attr "unit" "i387,*")
4821    (set_attr "athlon_decode" "*,direct")
4822    (set_attr "amdfam10_decode" "*,double")
4823    (set_attr "bdver1_decode" "*,direct")
4824    (set_attr "fp_int_src" "true")])
4825
4826 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_with_temp"
4827   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
4828         (float:MODEF
4829           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r,r,m")))
4830    (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m,m,X"))]
4831   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4832    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387"
4833   "#"
4834   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4835    (set_attr "mode" "<MODEF:MODE>")
4836    (set_attr "unit" "*,i387,*,*")
4837    (set_attr "athlon_decode" "*,*,double,direct")
4838    (set_attr "amdfam10_decode" "*,*,vector,double")
4839    (set_attr "bdver1_decode" "*,*,double,direct")
4840    (set_attr "fp_int_src" "true")])
4841
4842 (define_split
4843   [(set (match_operand:MODEF 0 "register_operand" "")
4844         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4845    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4846   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4847    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4848    && TARGET_INTER_UNIT_CONVERSIONS
4849    && reload_completed
4850    && (SSE_REG_P (operands[0])
4851        || (GET_CODE (operands[0]) == SUBREG
4852            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4853   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
4854
4855 (define_split
4856   [(set (match_operand:MODEF 0 "register_operand" "")
4857         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4858    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4859   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4860    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4861    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
4862    && reload_completed
4863    && (SSE_REG_P (operands[0])
4864        || (GET_CODE (operands[0]) == SUBREG
4865            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4866   [(set (match_dup 2) (match_dup 1))
4867    (set (match_dup 0) (float:MODEF (match_dup 2)))])
4868
4869 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_interunit"
4870   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
4871         (float:MODEF
4872           (match_operand:SWI48x 1 "nonimmediate_operand" "m,r,m")))]
4873   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4874    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4875    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4876   "@
4877    fild%Z1\t%1
4878    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}
4879    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4880   [(set_attr "type" "fmov,sseicvt,sseicvt")
4881    (set_attr "prefix" "orig,maybe_vex,maybe_vex")
4882    (set_attr "mode" "<MODEF:MODE>")
4883    (set (attr "prefix_rex")
4884      (if_then_else
4885        (and (eq_attr "prefix" "maybe_vex")
4886             (match_test "<SWI48x:MODE>mode == DImode"))
4887        (const_string "1")
4888        (const_string "*")))
4889    (set_attr "unit" "i387,*,*")
4890    (set_attr "athlon_decode" "*,double,direct")
4891    (set_attr "amdfam10_decode" "*,vector,double")
4892    (set_attr "bdver1_decode" "*,double,direct")
4893    (set_attr "fp_int_src" "true")])
4894
4895 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_nointerunit"
4896   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4897         (float:MODEF
4898           (match_operand:SWI48x 1 "memory_operand" "m,m")))]
4899   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4900    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4901    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4902   "@
4903    fild%Z1\t%1
4904    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4905   [(set_attr "type" "fmov,sseicvt")
4906    (set_attr "prefix" "orig,maybe_vex")
4907    (set_attr "mode" "<MODEF:MODE>")
4908    (set (attr "prefix_rex")
4909      (if_then_else
4910        (and (eq_attr "prefix" "maybe_vex")
4911             (match_test "<SWI48x:MODE>mode == DImode"))
4912        (const_string "1")
4913        (const_string "*")))
4914    (set_attr "athlon_decode" "*,direct")
4915    (set_attr "amdfam10_decode" "*,double")
4916    (set_attr "bdver1_decode" "*,direct")
4917    (set_attr "fp_int_src" "true")])
4918
4919 (define_insn "*floatsi<mode>2_vector_sse_with_temp"
4920   [(set (match_operand:MODEF 0 "register_operand" "=x,x,x")
4921         (float:MODEF
4922           (match_operand:SI 1 "nonimmediate_operand" "r,m,!x")))
4923    (clobber (match_operand:SI 2 "memory_operand" "=m,X,m"))]
4924   "TARGET_SSE2 && TARGET_SSE_MATH
4925    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4926   "#"
4927   [(set_attr "type" "sseicvt")
4928    (set_attr "mode" "<MODE>,<MODE>,<ssevecmode>")
4929    (set_attr "athlon_decode" "double,direct,double")
4930    (set_attr "amdfam10_decode" "vector,double,double")
4931    (set_attr "bdver1_decode" "double,direct,double")
4932    (set_attr "fp_int_src" "true")])
4933
4934 (define_insn "*floatsi<mode>2_vector_sse"
4935   [(set (match_operand:MODEF 0 "register_operand" "=x")
4936         (float:MODEF (match_operand:SI 1 "memory_operand" "m")))]
4937   "TARGET_SSE2 && TARGET_SSE_MATH
4938    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4939   "#"
4940   [(set_attr "type" "sseicvt")
4941    (set_attr "mode" "<MODE>")
4942    (set_attr "athlon_decode" "direct")
4943    (set_attr "amdfam10_decode" "double")
4944    (set_attr "bdver1_decode" "direct")
4945    (set_attr "fp_int_src" "true")])
4946
4947 (define_split
4948   [(set (match_operand:MODEF 0 "register_operand" "")
4949         (float:MODEF (match_operand:SI 1 "register_operand" "")))
4950    (clobber (match_operand:SI 2 "memory_operand" ""))]
4951   "TARGET_SSE2 && TARGET_SSE_MATH
4952    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
4953    && reload_completed
4954    && (SSE_REG_P (operands[0])
4955        || (GET_CODE (operands[0]) == SUBREG
4956            && SSE_REG_P (SUBREG_REG (operands[0]))))"
4957   [(const_int 0)]
4958 {
4959   rtx op1 = operands[1];
4960
4961   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
4962                                      <MODE>mode, 0);
4963   if (GET_CODE (op1) == SUBREG)
4964     op1 = SUBREG_REG (op1);
4965
4966   if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
4967     {
4968       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
4969       emit_insn (gen_sse2_loadld (operands[4],
4970                                   CONST0_RTX (V4SImode), operands[1]));
4971     }
4972   /* We can ignore possible trapping value in the
4973      high part of SSE register for non-trapping math. */
4974   else if (SSE_REG_P (op1) && !flag_trapping_math)
4975     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
4976   else
4977     {
4978       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
4979       emit_move_insn (operands[2], operands[1]);
4980       emit_insn (gen_sse2_loadld (operands[4],
4981                                   CONST0_RTX (V4SImode), operands[2]));
4982     }
4983   if (<ssevecmode>mode == V4SFmode)
4984     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
4985   else
4986     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
4987   DONE;
4988 })
4989
4990 (define_split
4991   [(set (match_operand:MODEF 0 "register_operand" "")
4992         (float:MODEF (match_operand:SI 1 "memory_operand" "")))
4993    (clobber (match_operand:SI 2 "memory_operand" ""))]
4994   "TARGET_SSE2 && TARGET_SSE_MATH
4995    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
4996    && reload_completed
4997    && (SSE_REG_P (operands[0])
4998        || (GET_CODE (operands[0]) == SUBREG
4999            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5000   [(const_int 0)]
5001 {
5002   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5003                                      <MODE>mode, 0);
5004   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5005
5006   emit_insn (gen_sse2_loadld (operands[4],
5007                               CONST0_RTX (V4SImode), operands[1]));
5008   if (<ssevecmode>mode == V4SFmode)
5009     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5010   else
5011     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5012   DONE;
5013 })
5014
5015 (define_split
5016   [(set (match_operand:MODEF 0 "register_operand" "")
5017         (float:MODEF (match_operand:SI 1 "register_operand" "")))]
5018   "TARGET_SSE2 && TARGET_SSE_MATH
5019    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5020    && reload_completed
5021    && (SSE_REG_P (operands[0])
5022        || (GET_CODE (operands[0]) == SUBREG
5023            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5024   [(const_int 0)]
5025 {
5026   rtx op1 = operands[1];
5027
5028   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5029                                      <MODE>mode, 0);
5030   if (GET_CODE (op1) == SUBREG)
5031     op1 = SUBREG_REG (op1);
5032
5033   if (GENERAL_REG_P (op1))
5034     {
5035       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5036       if (TARGET_INTER_UNIT_MOVES)
5037         emit_insn (gen_sse2_loadld (operands[4],
5038                                     CONST0_RTX (V4SImode), operands[1]));
5039       else
5040         {
5041           operands[5] = ix86_force_to_memory (GET_MODE (operands[1]),
5042                                               operands[1]);
5043           emit_insn (gen_sse2_loadld (operands[4],
5044                                       CONST0_RTX (V4SImode), operands[5]));
5045           ix86_free_from_memory (GET_MODE (operands[1]));
5046         }
5047     }
5048   /* We can ignore possible trapping value in the
5049      high part of SSE register for non-trapping math. */
5050   else if (SSE_REG_P (op1) && !flag_trapping_math)
5051     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5052   else
5053     gcc_unreachable ();
5054   if (<ssevecmode>mode == V4SFmode)
5055     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5056   else
5057     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5058   DONE;
5059 })
5060
5061 (define_split
5062   [(set (match_operand:MODEF 0 "register_operand" "")
5063         (float:MODEF (match_operand:SI 1 "memory_operand" "")))]
5064   "TARGET_SSE2 && TARGET_SSE_MATH
5065    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5066    && reload_completed
5067    && (SSE_REG_P (operands[0])
5068        || (GET_CODE (operands[0]) == SUBREG
5069            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5070   [(const_int 0)]
5071 {
5072   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5073                                      <MODE>mode, 0);
5074   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5075
5076   emit_insn (gen_sse2_loadld (operands[4],
5077                               CONST0_RTX (V4SImode), operands[1]));
5078   if (<ssevecmode>mode == V4SFmode)
5079     emit_insn (gen_floatv4siv4sf2 (operands[3], operands[4]));
5080   else
5081     emit_insn (gen_sse2_cvtdq2pd (operands[3], operands[4]));
5082   DONE;
5083 })
5084
5085 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_with_temp"
5086   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5087         (float:MODEF
5088           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))
5089   (clobber (match_operand:SWI48x 2 "memory_operand" "=m,X"))]
5090   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5091    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH"
5092   "#"
5093   [(set_attr "type" "sseicvt")
5094    (set_attr "mode" "<MODEF:MODE>")
5095    (set_attr "athlon_decode" "double,direct")
5096    (set_attr "amdfam10_decode" "vector,double")
5097    (set_attr "bdver1_decode" "double,direct")
5098    (set_attr "fp_int_src" "true")])
5099
5100 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_interunit"
5101   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5102         (float:MODEF
5103           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))]
5104   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5105    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5106    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5107   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5108   [(set_attr "type" "sseicvt")
5109    (set_attr "prefix" "maybe_vex")
5110    (set_attr "mode" "<MODEF:MODE>")
5111    (set (attr "prefix_rex")
5112      (if_then_else
5113        (and (eq_attr "prefix" "maybe_vex")
5114             (match_test "<SWI48x:MODE>mode == DImode"))
5115        (const_string "1")
5116        (const_string "*")))
5117    (set_attr "athlon_decode" "double,direct")
5118    (set_attr "amdfam10_decode" "vector,double")
5119    (set_attr "bdver1_decode" "double,direct")
5120    (set_attr "fp_int_src" "true")])
5121
5122 (define_split
5123   [(set (match_operand:MODEF 0 "register_operand" "")
5124         (float:MODEF (match_operand:SWI48x 1 "nonimmediate_operand" "")))
5125    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5126   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5127    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5128    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5129    && reload_completed
5130    && (SSE_REG_P (operands[0])
5131        || (GET_CODE (operands[0]) == SUBREG
5132            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5133   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5134
5135 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_nointerunit"
5136   [(set (match_operand:MODEF 0 "register_operand" "=x")
5137         (float:MODEF
5138           (match_operand:SWI48x 1 "memory_operand" "m")))]
5139   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5140    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5141    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5142   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5143   [(set_attr "type" "sseicvt")
5144    (set_attr "prefix" "maybe_vex")
5145    (set_attr "mode" "<MODEF:MODE>")
5146    (set (attr "prefix_rex")
5147      (if_then_else
5148        (and (eq_attr "prefix" "maybe_vex")
5149             (match_test "<SWI48x:MODE>mode == DImode"))
5150        (const_string "1")
5151        (const_string "*")))
5152    (set_attr "athlon_decode" "direct")
5153    (set_attr "amdfam10_decode" "double")
5154    (set_attr "bdver1_decode" "direct")
5155    (set_attr "fp_int_src" "true")])
5156
5157 (define_split
5158   [(set (match_operand:MODEF 0 "register_operand" "")
5159         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
5160    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5161   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5162    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5163    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5164    && reload_completed
5165    && (SSE_REG_P (operands[0])
5166        || (GET_CODE (operands[0]) == SUBREG
5167            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5168   [(set (match_dup 2) (match_dup 1))
5169    (set (match_dup 0) (float:MODEF (match_dup 2)))])
5170
5171 (define_split
5172   [(set (match_operand:MODEF 0 "register_operand" "")
5173         (float:MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5174    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5175   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5176    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5177    && reload_completed
5178    && (SSE_REG_P (operands[0])
5179        || (GET_CODE (operands[0]) == SUBREG
5180            && SSE_REG_P (SUBREG_REG (operands[0]))))"
5181   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5182
5183 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387_with_temp"
5184   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5185         (float:X87MODEF
5186           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r")))
5187   (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m"))]
5188   "TARGET_80387
5189    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5190   "@
5191    fild%Z1\t%1
5192    #"
5193   [(set_attr "type" "fmov,multi")
5194    (set_attr "mode" "<X87MODEF:MODE>")
5195    (set_attr "unit" "*,i387")
5196    (set_attr "fp_int_src" "true")])
5197
5198 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387"
5199   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5200         (float:X87MODEF
5201           (match_operand:SWI48x 1 "memory_operand" "m")))]
5202   "TARGET_80387
5203    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5204   "fild%Z1\t%1"
5205   [(set_attr "type" "fmov")
5206    (set_attr "mode" "<X87MODEF:MODE>")
5207    (set_attr "fp_int_src" "true")])
5208
5209 (define_split
5210   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5211         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))
5212    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5213   "TARGET_80387
5214    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5215    && reload_completed"
5216   [(set (match_dup 2) (match_dup 1))
5217    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
5218
5219 (define_split
5220   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5221         (float:X87MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5222    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5223   "TARGET_80387
5224    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5225    && reload_completed"
5226   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5227
5228 ;; Avoid store forwarding (partial memory) stall penalty
5229 ;; by passing DImode value through XMM registers.  */
5230
5231 (define_insn "floatdi<X87MODEF:mode>2_i387_with_xmm"
5232   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5233         (float:X87MODEF
5234           (match_operand:DI 1 "nonimmediate_operand" "m,?r")))
5235    (clobber (match_scratch:V4SI 3 "=X,x"))
5236    (clobber (match_scratch:V4SI 4 "=X,x"))
5237    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))]
5238   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5239    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5240    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)"
5241   "#"
5242   [(set_attr "type" "multi")
5243    (set_attr "mode" "<X87MODEF:MODE>")
5244    (set_attr "unit" "i387")
5245    (set_attr "fp_int_src" "true")])
5246
5247 (define_split
5248   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5249         (float:X87MODEF (match_operand:DI 1 "register_operand" "")))
5250    (clobber (match_scratch:V4SI 3 ""))
5251    (clobber (match_scratch:V4SI 4 ""))
5252    (clobber (match_operand:DI 2 "memory_operand" ""))]
5253   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5254    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5255    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5256    && reload_completed"
5257   [(set (match_dup 2) (match_dup 3))
5258    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5259 {
5260   /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
5261      Assemble the 64-bit DImode value in an xmm register.  */
5262   emit_insn (gen_sse2_loadld (operands[3], CONST0_RTX (V4SImode),
5263                               gen_rtx_SUBREG (SImode, operands[1], 0)));
5264   emit_insn (gen_sse2_loadld (operands[4], CONST0_RTX (V4SImode),
5265                               gen_rtx_SUBREG (SImode, operands[1], 4)));
5266   emit_insn (gen_vec_interleave_lowv4si (operands[3], operands[3],
5267                                          operands[4]));
5268
5269   operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
5270 })
5271
5272 (define_split
5273   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5274         (float:X87MODEF (match_operand:DI 1 "memory_operand" "")))
5275    (clobber (match_scratch:V4SI 3 ""))
5276    (clobber (match_scratch:V4SI 4 ""))
5277    (clobber (match_operand:DI 2 "memory_operand" ""))]
5278   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5279    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5280    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5281    && reload_completed"
5282   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5283
5284 ;; Avoid store forwarding (partial memory) stall penalty by extending
5285 ;; SImode value to DImode through XMM register instead of pushing two
5286 ;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES
5287 ;; targets benefit from this optimization. Also note that fild
5288 ;; loads from memory only.
5289
5290 (define_insn "*floatunssi<mode>2_1"
5291   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5292         (unsigned_float:X87MODEF
5293           (match_operand:SI 1 "nonimmediate_operand" "x,m")))
5294    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
5295    (clobber (match_scratch:SI 3 "=X,x"))]
5296   "!TARGET_64BIT
5297    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5298    && TARGET_SSE"
5299   "#"
5300   [(set_attr "type" "multi")
5301    (set_attr "mode" "<MODE>")])
5302
5303 (define_split
5304   [(set (match_operand:X87MODEF 0 "register_operand" "")
5305         (unsigned_float:X87MODEF
5306           (match_operand:SI 1 "register_operand" "")))
5307    (clobber (match_operand:DI 2 "memory_operand" ""))
5308    (clobber (match_scratch:SI 3 ""))]
5309   "!TARGET_64BIT
5310    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5311    && TARGET_SSE
5312    && reload_completed"
5313   [(set (match_dup 2) (match_dup 1))
5314    (set (match_dup 0)
5315         (float:X87MODEF (match_dup 2)))]
5316   "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);")
5317
5318 (define_split
5319   [(set (match_operand:X87MODEF 0 "register_operand" "")
5320         (unsigned_float:X87MODEF
5321           (match_operand:SI 1 "memory_operand" "")))
5322    (clobber (match_operand:DI 2 "memory_operand" ""))
5323    (clobber (match_scratch:SI 3 ""))]
5324   "!TARGET_64BIT
5325    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5326    && TARGET_SSE
5327    && reload_completed"
5328   [(set (match_dup 2) (match_dup 3))
5329    (set (match_dup 0)
5330         (float:X87MODEF (match_dup 2)))]
5331 {
5332   emit_move_insn (operands[3], operands[1]);
5333   operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0);
5334 })
5335
5336 (define_expand "floatunssi<mode>2"
5337   [(parallel
5338      [(set (match_operand:X87MODEF 0 "register_operand" "")
5339            (unsigned_float:X87MODEF
5340              (match_operand:SI 1 "nonimmediate_operand" "")))
5341       (clobber (match_dup 2))
5342       (clobber (match_scratch:SI 3 ""))])]
5343   "!TARGET_64BIT
5344    && ((TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5345         && TARGET_SSE)
5346        || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
5347 {
5348   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5349     {
5350       ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5351       DONE;
5352     }
5353   else
5354     operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
5355 })
5356
5357 (define_expand "floatunsdisf2"
5358   [(use (match_operand:SF 0 "register_operand" ""))
5359    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5360   "TARGET_64BIT && TARGET_SSE_MATH"
5361   "x86_emit_floatuns (operands); DONE;")
5362
5363 (define_expand "floatunsdidf2"
5364   [(use (match_operand:DF 0 "register_operand" ""))
5365    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5366   "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5367    && TARGET_SSE2 && TARGET_SSE_MATH"
5368 {
5369   if (TARGET_64BIT)
5370     x86_emit_floatuns (operands);
5371   else
5372     ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5373   DONE;
5374 })
5375 \f
5376 ;; Load effective address instructions
5377
5378 (define_insn_and_split "*lea<mode>"
5379   [(set (match_operand:SWI48 0 "register_operand" "=r")
5380         (match_operand:SWI48 1 "lea_address_operand" "p"))]
5381   ""
5382 {
5383   rtx addr = operands[1];
5384
5385   if (SImode_address_operand (addr, VOIDmode))
5386     {
5387       gcc_assert (TARGET_64BIT);
5388       return "lea{l}\t{%E1, %k0|%k0, %E1}";
5389     }
5390   else 
5391     return "lea{<imodesuffix>}\t{%E1, %0|%0, %E1}";
5392 }
5393   "reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
5394   [(const_int 0)]
5395 {
5396   ix86_split_lea_for_addr (operands, <MODE>mode);
5397   DONE;
5398 }
5399   [(set_attr "type" "lea")
5400    (set (attr "mode")
5401      (if_then_else
5402        (match_operand 1 "SImode_address_operand")
5403        (const_string "SI")
5404        (const_string "<MODE>")))])
5405 \f
5406 ;; Add instructions
5407
5408 (define_expand "add<mode>3"
5409   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
5410         (plus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
5411                     (match_operand:SDWIM 2 "<general_operand>" "")))]
5412   ""
5413   "ix86_expand_binary_operator (PLUS, <MODE>mode, operands); DONE;")
5414
5415 (define_insn_and_split "*add<dwi>3_doubleword"
5416   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
5417         (plus:<DWI>
5418           (match_operand:<DWI> 1 "nonimmediate_operand" "%0,0")
5419           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
5420    (clobber (reg:CC FLAGS_REG))]
5421   "ix86_binary_operator_ok (PLUS, <DWI>mode, operands)"
5422   "#"
5423   "reload_completed"
5424   [(parallel [(set (reg:CC FLAGS_REG)
5425                    (unspec:CC [(match_dup 1) (match_dup 2)]
5426                               UNSPEC_ADD_CARRY))
5427               (set (match_dup 0)
5428                    (plus:DWIH (match_dup 1) (match_dup 2)))])
5429    (parallel [(set (match_dup 3)
5430                    (plus:DWIH
5431                      (match_dup 4)
5432                      (plus:DWIH
5433                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
5434                        (match_dup 5))))
5435               (clobber (reg:CC FLAGS_REG))])]
5436   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
5437
5438 (define_insn "*add<mode>3_cc"
5439   [(set (reg:CC FLAGS_REG)
5440         (unspec:CC
5441           [(match_operand:SWI48 1 "nonimmediate_operand" "%0,0")
5442            (match_operand:SWI48 2 "<general_operand>" "r<i>,rm")]
5443           UNSPEC_ADD_CARRY))
5444    (set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
5445         (plus:SWI48 (match_dup 1) (match_dup 2)))]
5446   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5447   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
5448   [(set_attr "type" "alu")
5449    (set_attr "mode" "<MODE>")])
5450
5451 (define_insn "addqi3_cc"
5452   [(set (reg:CC FLAGS_REG)
5453         (unspec:CC
5454           [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5455            (match_operand:QI 2 "general_operand" "qn,qm")]
5456           UNSPEC_ADD_CARRY))
5457    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5458         (plus:QI (match_dup 1) (match_dup 2)))]
5459   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5460   "add{b}\t{%2, %0|%0, %2}"
5461   [(set_attr "type" "alu")
5462    (set_attr "mode" "QI")])
5463
5464 (define_insn "*add<mode>_1"
5465   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,rm,r,r")
5466         (plus:SWI48
5467           (match_operand:SWI48 1 "nonimmediate_operand" "%0,0,r,r")
5468           (match_operand:SWI48 2 "x86_64_general_operand" "rme,re,0,le")))
5469    (clobber (reg:CC FLAGS_REG))]
5470   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5471 {
5472   switch (get_attr_type (insn))
5473     {
5474     case TYPE_LEA:
5475       return "#";
5476
5477     case TYPE_INCDEC:
5478       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5479       if (operands[2] == const1_rtx)
5480         return "inc{<imodesuffix>}\t%0";
5481       else
5482         {
5483           gcc_assert (operands[2] == constm1_rtx);
5484           return "dec{<imodesuffix>}\t%0";
5485         }
5486
5487     default:
5488       /* For most processors, ADD is faster than LEA.  This alternative
5489          was added to use ADD as much as possible.  */
5490       if (which_alternative == 2)
5491         {
5492           rtx tmp;
5493           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5494         }
5495         
5496       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5497       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5498         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5499
5500       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5501     }
5502 }
5503   [(set (attr "type")
5504      (cond [(eq_attr "alternative" "3")
5505               (const_string "lea")
5506             (match_operand:SWI48 2 "incdec_operand" "")
5507               (const_string "incdec")
5508            ]
5509            (const_string "alu")))
5510    (set (attr "length_immediate")
5511       (if_then_else
5512         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5513         (const_string "1")
5514         (const_string "*")))
5515    (set_attr "mode" "<MODE>")])
5516
5517 ;; It may seem that nonimmediate operand is proper one for operand 1.
5518 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5519 ;; we take care in ix86_binary_operator_ok to not allow two memory
5520 ;; operands so proper swapping will be done in reload.  This allow
5521 ;; patterns constructed from addsi_1 to match.
5522
5523 (define_insn "addsi_1_zext"
5524   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
5525         (zero_extend:DI
5526           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r,r")
5527                    (match_operand:SI 2 "x86_64_general_operand" "rme,0,le"))))
5528    (clobber (reg:CC FLAGS_REG))]
5529   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5530 {
5531   switch (get_attr_type (insn))
5532     {
5533     case TYPE_LEA:
5534       return "#";
5535
5536     case TYPE_INCDEC:
5537       if (operands[2] == const1_rtx)
5538         return "inc{l}\t%k0";
5539       else
5540         {
5541           gcc_assert (operands[2] == constm1_rtx);
5542           return "dec{l}\t%k0";
5543         }
5544
5545     default:
5546       /* For most processors, ADD is faster than LEA.  This alternative
5547          was added to use ADD as much as possible.  */
5548       if (which_alternative == 1)
5549         {
5550           rtx tmp;
5551           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5552         }
5553
5554       if (x86_maybe_negate_const_int (&operands[2], SImode))
5555         return "sub{l}\t{%2, %k0|%k0, %2}";
5556
5557       return "add{l}\t{%2, %k0|%k0, %2}";
5558     }
5559 }
5560   [(set (attr "type")
5561      (cond [(eq_attr "alternative" "2")
5562               (const_string "lea")
5563             (match_operand:SI 2 "incdec_operand" "")
5564               (const_string "incdec")
5565            ]
5566            (const_string "alu")))
5567    (set (attr "length_immediate")
5568       (if_then_else
5569         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5570         (const_string "1")
5571         (const_string "*")))
5572    (set_attr "mode" "SI")])
5573
5574 (define_insn "*addhi_1"
5575   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r,Yp")
5576         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r,Yp")
5577                  (match_operand:HI 2 "general_operand" "rn,rm,0,ln")))
5578    (clobber (reg:CC FLAGS_REG))]
5579   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5580 {
5581   switch (get_attr_type (insn))
5582     {
5583     case TYPE_LEA:
5584       return "#";
5585
5586     case TYPE_INCDEC:
5587       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5588       if (operands[2] == const1_rtx)
5589         return "inc{w}\t%0";
5590       else
5591         {
5592           gcc_assert (operands[2] == constm1_rtx);
5593           return "dec{w}\t%0";
5594         }
5595
5596     default:
5597       /* For most processors, ADD is faster than LEA.  This alternative
5598          was added to use ADD as much as possible.  */
5599       if (which_alternative == 2)
5600         {
5601           rtx tmp;
5602           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5603         }
5604
5605       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5606       if (x86_maybe_negate_const_int (&operands[2], HImode))
5607         return "sub{w}\t{%2, %0|%0, %2}";
5608
5609       return "add{w}\t{%2, %0|%0, %2}";
5610     }
5611 }
5612   [(set (attr "type")
5613      (cond [(eq_attr "alternative" "3")
5614               (const_string "lea")
5615             (match_operand:HI 2 "incdec_operand" "")
5616               (const_string "incdec")
5617            ]
5618            (const_string "alu")))
5619    (set (attr "length_immediate")
5620       (if_then_else
5621         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5622         (const_string "1")
5623         (const_string "*")))
5624    (set_attr "mode" "HI,HI,HI,SI")])
5625
5626 ;; %%% Potential partial reg stall on alternatives 3 and 4.  What to do?
5627 (define_insn "*addqi_1"
5628   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,q,r,r,Yp")
5629         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,q,0,r,Yp")
5630                  (match_operand:QI 2 "general_operand" "qn,qm,0,rn,0,ln")))
5631    (clobber (reg:CC FLAGS_REG))]
5632   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5633 {
5634   bool widen = (which_alternative == 3 || which_alternative == 4);
5635
5636   switch (get_attr_type (insn))
5637     {
5638     case TYPE_LEA:
5639       return "#";
5640
5641     case TYPE_INCDEC:
5642       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5643       if (operands[2] == const1_rtx)
5644         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
5645       else
5646         {
5647           gcc_assert (operands[2] == constm1_rtx);
5648           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
5649         }
5650
5651     default:
5652       /* For most processors, ADD is faster than LEA.  These alternatives
5653          were added to use ADD as much as possible.  */
5654       if (which_alternative == 2 || which_alternative == 4)
5655         {
5656           rtx tmp;
5657           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5658         }
5659
5660       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5661       if (x86_maybe_negate_const_int (&operands[2], QImode))
5662         {
5663           if (widen)
5664             return "sub{l}\t{%2, %k0|%k0, %2}";
5665           else
5666             return "sub{b}\t{%2, %0|%0, %2}";
5667         }
5668       if (widen)
5669         return "add{l}\t{%k2, %k0|%k0, %k2}";
5670       else
5671         return "add{b}\t{%2, %0|%0, %2}";
5672     }
5673 }
5674   [(set (attr "type")
5675      (cond [(eq_attr "alternative" "5")
5676               (const_string "lea")
5677             (match_operand:QI 2 "incdec_operand" "")
5678               (const_string "incdec")
5679            ]
5680            (const_string "alu")))
5681    (set (attr "length_immediate")
5682       (if_then_else
5683         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5684         (const_string "1")
5685         (const_string "*")))
5686    (set_attr "mode" "QI,QI,QI,SI,SI,SI")])
5687
5688 (define_insn "*addqi_1_slp"
5689   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
5690         (plus:QI (match_dup 0)
5691                  (match_operand:QI 1 "general_operand" "qn,qm")))
5692    (clobber (reg:CC FLAGS_REG))]
5693   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
5694    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
5695 {
5696   switch (get_attr_type (insn))
5697     {
5698     case TYPE_INCDEC:
5699       if (operands[1] == const1_rtx)
5700         return "inc{b}\t%0";
5701       else
5702         {
5703           gcc_assert (operands[1] == constm1_rtx);
5704           return "dec{b}\t%0";
5705         }
5706
5707     default:
5708       if (x86_maybe_negate_const_int (&operands[1], QImode))
5709         return "sub{b}\t{%1, %0|%0, %1}";
5710
5711       return "add{b}\t{%1, %0|%0, %1}";
5712     }
5713 }
5714   [(set (attr "type")
5715      (if_then_else (match_operand:QI 1 "incdec_operand" "")
5716         (const_string "incdec")
5717         (const_string "alu1")))
5718    (set (attr "memory")
5719      (if_then_else (match_operand 1 "memory_operand" "")
5720         (const_string "load")
5721         (const_string "none")))
5722    (set_attr "mode" "QI")])
5723
5724 ;; Split non destructive adds if we cannot use lea.
5725 (define_split
5726   [(set (match_operand:SWI48 0 "register_operand" "")
5727         (plus:SWI48 (match_operand:SWI48 1 "register_operand" "")
5728               (match_operand:SWI48 2 "nonmemory_operand" "")))
5729    (clobber (reg:CC FLAGS_REG))]
5730   "reload_completed && ix86_avoid_lea_for_add (insn, operands)"
5731   [(set (match_dup 0) (match_dup 1))
5732    (parallel [(set (match_dup 0) (plus:<MODE> (match_dup 0) (match_dup 2)))
5733               (clobber (reg:CC FLAGS_REG))])])
5734
5735 ;; Convert add to the lea pattern to avoid flags dependency.
5736 (define_split
5737   [(set (match_operand:SWI 0 "register_operand" "")
5738         (plus:SWI (match_operand:SWI 1 "register_operand" "")
5739                   (match_operand:SWI 2 "<nonmemory_operand>" "")))
5740    (clobber (reg:CC FLAGS_REG))]
5741   "reload_completed && ix86_lea_for_add_ok (insn, operands)" 
5742   [(const_int 0)]
5743 {
5744   enum machine_mode mode = <MODE>mode;
5745   rtx pat;
5746
5747   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
5748     { 
5749       mode = SImode; 
5750       operands[0] = gen_lowpart (mode, operands[0]);
5751       operands[1] = gen_lowpart (mode, operands[1]);
5752       operands[2] = gen_lowpart (mode, operands[2]);
5753     }
5754
5755   pat = gen_rtx_PLUS (mode, operands[1], operands[2]);
5756
5757   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5758   DONE;
5759 })
5760
5761 ;; Convert add to the lea pattern to avoid flags dependency.
5762 (define_split
5763   [(set (match_operand:DI 0 "register_operand" "")
5764         (zero_extend:DI
5765           (plus:SI (match_operand:SI 1 "register_operand" "")
5766                    (match_operand:SI 2 "x86_64_nonmemory_operand" ""))))
5767    (clobber (reg:CC FLAGS_REG))]
5768   "TARGET_64BIT && reload_completed && ix86_lea_for_add_ok (insn, operands)"
5769   [(set (match_dup 0)
5770         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))])
5771
5772 (define_insn "*add<mode>_2"
5773   [(set (reg FLAGS_REG)
5774         (compare
5775           (plus:SWI
5776             (match_operand:SWI 1 "nonimmediate_operand" "%0,0,<r>")
5777             (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>,0"))
5778           (const_int 0)))
5779    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m,<r>")
5780         (plus:SWI (match_dup 1) (match_dup 2)))]
5781   "ix86_match_ccmode (insn, CCGOCmode)
5782    && ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5783 {
5784   switch (get_attr_type (insn))
5785     {
5786     case TYPE_INCDEC:
5787       if (operands[2] == const1_rtx)
5788         return "inc{<imodesuffix>}\t%0";
5789       else
5790         {
5791           gcc_assert (operands[2] == constm1_rtx);
5792           return "dec{<imodesuffix>}\t%0";
5793         }
5794
5795     default:
5796       if (which_alternative == 2)
5797         {
5798           rtx tmp;
5799           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5800         }
5801         
5802       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5803       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5804         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5805
5806       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5807     }
5808 }
5809   [(set (attr "type")
5810      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5811         (const_string "incdec")
5812         (const_string "alu")))
5813    (set (attr "length_immediate")
5814       (if_then_else
5815         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5816         (const_string "1")
5817         (const_string "*")))
5818    (set_attr "mode" "<MODE>")])
5819
5820 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5821 (define_insn "*addsi_2_zext"
5822   [(set (reg FLAGS_REG)
5823         (compare
5824           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5825                    (match_operand:SI 2 "x86_64_general_operand" "rme,0"))
5826           (const_int 0)))
5827    (set (match_operand:DI 0 "register_operand" "=r,r")
5828         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5829   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5830    && ix86_binary_operator_ok (PLUS, SImode, operands)"
5831 {
5832   switch (get_attr_type (insn))
5833     {
5834     case TYPE_INCDEC:
5835       if (operands[2] == const1_rtx)
5836         return "inc{l}\t%k0";
5837       else
5838         {
5839           gcc_assert (operands[2] == constm1_rtx);
5840           return "dec{l}\t%k0";
5841         }
5842
5843     default:
5844       if (which_alternative == 1)
5845         {
5846           rtx tmp;
5847           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5848         }
5849
5850       if (x86_maybe_negate_const_int (&operands[2], SImode))
5851         return "sub{l}\t{%2, %k0|%k0, %2}";
5852
5853       return "add{l}\t{%2, %k0|%k0, %2}";
5854     }
5855 }
5856   [(set (attr "type")
5857      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5858         (const_string "incdec")
5859         (const_string "alu")))
5860    (set (attr "length_immediate")
5861       (if_then_else
5862         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5863         (const_string "1")
5864         (const_string "*")))
5865    (set_attr "mode" "SI")])
5866
5867 (define_insn "*add<mode>_3"
5868   [(set (reg FLAGS_REG)
5869         (compare
5870           (neg:SWI (match_operand:SWI 2 "<general_operand>" "<g>,0"))
5871           (match_operand:SWI 1 "nonimmediate_operand" "%0,<r>")))
5872    (clobber (match_scratch:SWI 0 "=<r>,<r>"))]
5873   "ix86_match_ccmode (insn, CCZmode)
5874    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
5875 {
5876   switch (get_attr_type (insn))
5877     {
5878     case TYPE_INCDEC:
5879       if (operands[2] == const1_rtx)
5880         return "inc{<imodesuffix>}\t%0";
5881       else
5882         {
5883           gcc_assert (operands[2] == constm1_rtx);
5884           return "dec{<imodesuffix>}\t%0";
5885         }
5886
5887     default:
5888       if (which_alternative == 1)
5889         {
5890           rtx tmp;
5891           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5892         }
5893
5894       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5895       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5896         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5897
5898       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5899     }
5900 }
5901   [(set (attr "type")
5902      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5903         (const_string "incdec")
5904         (const_string "alu")))
5905    (set (attr "length_immediate")
5906       (if_then_else
5907         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5908         (const_string "1")
5909         (const_string "*")))
5910    (set_attr "mode" "<MODE>")])
5911
5912 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5913 (define_insn "*addsi_3_zext"
5914   [(set (reg FLAGS_REG)
5915         (compare
5916           (neg:SI (match_operand:SI 2 "x86_64_general_operand" "rme,0"))
5917           (match_operand:SI 1 "nonimmediate_operand" "%0,r")))
5918    (set (match_operand:DI 0 "register_operand" "=r,r")
5919         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5920   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5921    && ix86_binary_operator_ok (PLUS, SImode, operands)"
5922 {
5923   switch (get_attr_type (insn))
5924     {
5925     case TYPE_INCDEC:
5926       if (operands[2] == const1_rtx)
5927         return "inc{l}\t%k0";
5928       else
5929         {
5930           gcc_assert (operands[2] == constm1_rtx);
5931           return "dec{l}\t%k0";
5932         }
5933
5934     default:
5935       if (which_alternative == 1)
5936         {
5937           rtx tmp;
5938           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5939         }
5940
5941       if (x86_maybe_negate_const_int (&operands[2], SImode))
5942         return "sub{l}\t{%2, %k0|%k0, %2}";
5943
5944       return "add{l}\t{%2, %k0|%k0, %2}";
5945     }
5946 }
5947   [(set (attr "type")
5948      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5949         (const_string "incdec")
5950         (const_string "alu")))
5951    (set (attr "length_immediate")
5952       (if_then_else
5953         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5954         (const_string "1")
5955         (const_string "*")))
5956    (set_attr "mode" "SI")])
5957
5958 ; For comparisons against 1, -1 and 128, we may generate better code
5959 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5960 ; is matched then.  We can't accept general immediate, because for
5961 ; case of overflows,  the result is messed up.
5962 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5963 ; only for comparisons not depending on it.
5964
5965 (define_insn "*adddi_4"
5966   [(set (reg FLAGS_REG)
5967         (compare
5968           (match_operand:DI 1 "nonimmediate_operand" "0")
5969           (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5970    (clobber (match_scratch:DI 0 "=rm"))]
5971   "TARGET_64BIT
5972    && ix86_match_ccmode (insn, CCGCmode)"
5973 {
5974   switch (get_attr_type (insn))
5975     {
5976     case TYPE_INCDEC:
5977       if (operands[2] == constm1_rtx)
5978         return "inc{q}\t%0";
5979       else
5980         {
5981           gcc_assert (operands[2] == const1_rtx);
5982           return "dec{q}\t%0";
5983         }
5984
5985     default:
5986       if (x86_maybe_negate_const_int (&operands[2], DImode))
5987         return "add{q}\t{%2, %0|%0, %2}";
5988
5989       return "sub{q}\t{%2, %0|%0, %2}";
5990     }
5991 }
5992   [(set (attr "type")
5993      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5994         (const_string "incdec")
5995         (const_string "alu")))
5996    (set (attr "length_immediate")
5997       (if_then_else
5998         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5999         (const_string "1")
6000         (const_string "*")))
6001    (set_attr "mode" "DI")])
6002
6003 ; For comparisons against 1, -1 and 128, we may generate better code
6004 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6005 ; is matched then.  We can't accept general immediate, because for
6006 ; case of overflows,  the result is messed up.
6007 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6008 ; only for comparisons not depending on it.
6009
6010 (define_insn "*add<mode>_4"
6011   [(set (reg FLAGS_REG)
6012         (compare
6013           (match_operand:SWI124 1 "nonimmediate_operand" "0")
6014           (match_operand:SWI124 2 "const_int_operand" "n")))
6015    (clobber (match_scratch:SWI124 0 "=<r>m"))]
6016   "ix86_match_ccmode (insn, CCGCmode)"
6017 {
6018   switch (get_attr_type (insn))
6019     {
6020     case TYPE_INCDEC:
6021       if (operands[2] == constm1_rtx)
6022         return "inc{<imodesuffix>}\t%0";
6023       else
6024         {
6025           gcc_assert (operands[2] == const1_rtx);
6026           return "dec{<imodesuffix>}\t%0";
6027         }
6028
6029     default:
6030       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6031         return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6032
6033       return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6034     }
6035 }
6036   [(set (attr "type")
6037      (if_then_else (match_operand:<MODE> 2 "incdec_operand" "")
6038         (const_string "incdec")
6039         (const_string "alu")))
6040    (set (attr "length_immediate")
6041       (if_then_else
6042         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6043         (const_string "1")
6044         (const_string "*")))
6045    (set_attr "mode" "<MODE>")])
6046
6047 (define_insn "*add<mode>_5"
6048   [(set (reg FLAGS_REG)
6049         (compare
6050           (plus:SWI
6051             (match_operand:SWI 1 "nonimmediate_operand" "%0,<r>")
6052             (match_operand:SWI 2 "<general_operand>" "<g>,0"))
6053           (const_int 0)))
6054    (clobber (match_scratch:SWI 0 "=<r>,<r>"))]
6055   "ix86_match_ccmode (insn, CCGOCmode)
6056    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6057 {
6058   switch (get_attr_type (insn))
6059     {
6060     case TYPE_INCDEC:
6061       if (operands[2] == const1_rtx)
6062         return "inc{<imodesuffix>}\t%0";
6063       else
6064         {
6065           gcc_assert (operands[2] == constm1_rtx);
6066           return "dec{<imodesuffix>}\t%0";
6067         }
6068
6069     default:
6070       if (which_alternative == 1)
6071         {
6072           rtx tmp;
6073           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
6074         }
6075
6076       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6077       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6078         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6079
6080       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6081     }
6082 }
6083   [(set (attr "type")
6084      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
6085         (const_string "incdec")
6086         (const_string "alu")))
6087    (set (attr "length_immediate")
6088       (if_then_else
6089         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6090         (const_string "1")
6091         (const_string "*")))
6092    (set_attr "mode" "<MODE>")])
6093
6094 (define_insn "*addqi_ext_1_rex64"
6095   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6096                          (const_int 8)
6097                          (const_int 8))
6098         (plus:SI
6099           (zero_extract:SI
6100             (match_operand 1 "ext_register_operand" "0")
6101             (const_int 8)
6102             (const_int 8))
6103           (match_operand:QI 2 "nonmemory_operand" "Qn")))
6104    (clobber (reg:CC FLAGS_REG))]
6105   "TARGET_64BIT"
6106 {
6107   switch (get_attr_type (insn))
6108     {
6109     case TYPE_INCDEC:
6110       if (operands[2] == const1_rtx)
6111         return "inc{b}\t%h0";
6112       else
6113         {
6114           gcc_assert (operands[2] == constm1_rtx);
6115           return "dec{b}\t%h0";
6116         }
6117
6118     default:
6119       return "add{b}\t{%2, %h0|%h0, %2}";
6120     }
6121 }
6122   [(set (attr "type")
6123      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6124         (const_string "incdec")
6125         (const_string "alu")))
6126    (set_attr "modrm" "1")
6127    (set_attr "mode" "QI")])
6128
6129 (define_insn "addqi_ext_1"
6130   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6131                          (const_int 8)
6132                          (const_int 8))
6133         (plus:SI
6134           (zero_extract:SI
6135             (match_operand 1 "ext_register_operand" "0")
6136             (const_int 8)
6137             (const_int 8))
6138           (match_operand:QI 2 "general_operand" "Qmn")))
6139    (clobber (reg:CC FLAGS_REG))]
6140   "!TARGET_64BIT"
6141 {
6142   switch (get_attr_type (insn))
6143     {
6144     case TYPE_INCDEC:
6145       if (operands[2] == const1_rtx)
6146         return "inc{b}\t%h0";
6147       else
6148         {
6149           gcc_assert (operands[2] == constm1_rtx);
6150           return "dec{b}\t%h0";
6151         }
6152
6153     default:
6154       return "add{b}\t{%2, %h0|%h0, %2}";
6155     }
6156 }
6157   [(set (attr "type")
6158      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6159         (const_string "incdec")
6160         (const_string "alu")))
6161    (set_attr "modrm" "1")
6162    (set_attr "mode" "QI")])
6163
6164 (define_insn "*addqi_ext_2"
6165   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6166                          (const_int 8)
6167                          (const_int 8))
6168         (plus:SI
6169           (zero_extract:SI
6170             (match_operand 1 "ext_register_operand" "%0")
6171             (const_int 8)
6172             (const_int 8))
6173           (zero_extract:SI
6174             (match_operand 2 "ext_register_operand" "Q")
6175             (const_int 8)
6176             (const_int 8))))
6177    (clobber (reg:CC FLAGS_REG))]
6178   ""
6179   "add{b}\t{%h2, %h0|%h0, %h2}"
6180   [(set_attr "type" "alu")
6181    (set_attr "mode" "QI")])
6182
6183 ;; The lea patterns for modes less than 32 bits need to be matched by
6184 ;; several insns converted to real lea by splitters.
6185
6186 (define_insn_and_split "*lea_general_1"
6187   [(set (match_operand 0 "register_operand" "=r")
6188         (plus (plus (match_operand 1 "index_register_operand" "l")
6189                     (match_operand 2 "register_operand" "r"))
6190               (match_operand 3 "immediate_operand" "i")))]
6191   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6192    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6193    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6194    && GET_MODE (operands[0]) == GET_MODE (operands[2])
6195    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6196        || GET_MODE (operands[3]) == VOIDmode)"
6197   "#"
6198   "&& reload_completed"
6199   [(const_int 0)]
6200 {
6201   enum machine_mode mode = SImode;
6202   rtx pat;
6203
6204   operands[0] = gen_lowpart (mode, operands[0]);
6205   operands[1] = gen_lowpart (mode, operands[1]);
6206   operands[2] = gen_lowpart (mode, operands[2]);
6207   operands[3] = gen_lowpart (mode, operands[3]);
6208
6209   pat = gen_rtx_PLUS (mode, gen_rtx_PLUS (mode, operands[1], operands[2]),
6210                       operands[3]);
6211
6212   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6213   DONE;
6214 }
6215   [(set_attr "type" "lea")
6216    (set_attr "mode" "SI")])
6217
6218 (define_insn_and_split "*lea_general_2"
6219   [(set (match_operand 0 "register_operand" "=r")
6220         (plus (mult (match_operand 1 "index_register_operand" "l")
6221                     (match_operand 2 "const248_operand" "n"))
6222               (match_operand 3 "nonmemory_operand" "ri")))]
6223   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6224    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6225    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6226    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6227        || GET_MODE (operands[3]) == VOIDmode)"
6228   "#"
6229   "&& reload_completed"
6230   [(const_int 0)]
6231 {
6232   enum machine_mode mode = SImode;
6233   rtx pat;
6234
6235   operands[0] = gen_lowpart (mode, operands[0]);
6236   operands[1] = gen_lowpart (mode, operands[1]);
6237   operands[3] = gen_lowpart (mode, operands[3]);
6238
6239   pat = gen_rtx_PLUS (mode, gen_rtx_MULT (mode, operands[1], operands[2]),
6240                       operands[3]);
6241
6242   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6243   DONE;
6244 }
6245   [(set_attr "type" "lea")
6246    (set_attr "mode" "SI")])
6247
6248 (define_insn_and_split "*lea_general_3"
6249   [(set (match_operand 0 "register_operand" "=r")
6250         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
6251                           (match_operand 2 "const248_operand" "n"))
6252                     (match_operand 3 "register_operand" "r"))
6253               (match_operand 4 "immediate_operand" "i")))]
6254   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6255    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6256    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6257    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
6258   "#"
6259   "&& reload_completed"
6260   [(const_int 0)]
6261 {
6262   enum machine_mode mode = SImode;
6263   rtx pat;
6264
6265   operands[0] = gen_lowpart (mode, operands[0]);
6266   operands[1] = gen_lowpart (mode, operands[1]);
6267   operands[3] = gen_lowpart (mode, operands[3]);
6268   operands[4] = gen_lowpart (mode, operands[4]);
6269
6270   pat = gen_rtx_PLUS (mode,
6271                       gen_rtx_PLUS (mode,
6272                                     gen_rtx_MULT (mode, operands[1],
6273                                                         operands[2]),
6274                                     operands[3]),
6275                       operands[4]);
6276
6277   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6278   DONE;
6279 }
6280   [(set_attr "type" "lea")
6281    (set_attr "mode" "SI")])
6282
6283 (define_insn_and_split "*lea_general_4"
6284   [(set (match_operand 0 "register_operand" "=r")
6285         (any_or (ashift
6286                   (match_operand 1 "index_register_operand" "l")
6287                   (match_operand 2 "const_int_operand" "n"))
6288                 (match_operand 3 "const_int_operand" "n")))]
6289   "(((GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6290       && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)))
6291     || GET_MODE (operands[0]) == SImode
6292     || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
6293    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6294    && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) - 1 < 3
6295    && ((unsigned HOST_WIDE_INT) INTVAL (operands[3])
6296        < ((unsigned HOST_WIDE_INT) 1 << INTVAL (operands[2])))"
6297   "#"
6298   "&& reload_completed"
6299   [(const_int 0)]
6300 {
6301   enum machine_mode mode = GET_MODE (operands[0]);
6302   rtx pat;
6303
6304   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
6305     { 
6306       mode = SImode; 
6307       operands[0] = gen_lowpart (mode, operands[0]);
6308       operands[1] = gen_lowpart (mode, operands[1]);
6309     }
6310
6311   operands[2] = GEN_INT (1 << INTVAL (operands[2]));
6312
6313   pat = plus_constant (gen_rtx_MULT (mode, operands[1], operands[2]),
6314                        INTVAL (operands[3]));
6315
6316   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6317   DONE;
6318 }
6319   [(set_attr "type" "lea")
6320    (set (attr "mode")
6321       (if_then_else (match_operand:DI 0 "" "")
6322         (const_string "DI")
6323         (const_string "SI")))])
6324 \f
6325 ;; Subtract instructions
6326
6327 (define_expand "sub<mode>3"
6328   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
6329         (minus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
6330                      (match_operand:SDWIM 2 "<general_operand>" "")))]
6331   ""
6332   "ix86_expand_binary_operator (MINUS, <MODE>mode, operands); DONE;")
6333
6334 (define_insn_and_split "*sub<dwi>3_doubleword"
6335   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
6336         (minus:<DWI>
6337           (match_operand:<DWI> 1 "nonimmediate_operand" "0,0")
6338           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
6339    (clobber (reg:CC FLAGS_REG))]
6340   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6341   "#"
6342   "reload_completed"
6343   [(parallel [(set (reg:CC FLAGS_REG)
6344                    (compare:CC (match_dup 1) (match_dup 2)))
6345               (set (match_dup 0)
6346                    (minus:DWIH (match_dup 1) (match_dup 2)))])
6347    (parallel [(set (match_dup 3)
6348                    (minus:DWIH
6349                      (match_dup 4)
6350                      (plus:DWIH
6351                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
6352                        (match_dup 5))))
6353               (clobber (reg:CC FLAGS_REG))])]
6354   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
6355
6356 (define_insn "*sub<mode>_1"
6357   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6358         (minus:SWI
6359           (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6360           (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6361    (clobber (reg:CC FLAGS_REG))]
6362   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6363   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6364   [(set_attr "type" "alu")
6365    (set_attr "mode" "<MODE>")])
6366
6367 (define_insn "*subsi_1_zext"
6368   [(set (match_operand:DI 0 "register_operand" "=r")
6369         (zero_extend:DI
6370           (minus:SI (match_operand:SI 1 "register_operand" "0")
6371                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
6372    (clobber (reg:CC FLAGS_REG))]
6373   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6374   "sub{l}\t{%2, %k0|%k0, %2}"
6375   [(set_attr "type" "alu")
6376    (set_attr "mode" "SI")])
6377
6378 (define_insn "*subqi_1_slp"
6379   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6380         (minus:QI (match_dup 0)
6381                   (match_operand:QI 1 "general_operand" "qn,qm")))
6382    (clobber (reg:CC FLAGS_REG))]
6383   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6384    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6385   "sub{b}\t{%1, %0|%0, %1}"
6386   [(set_attr "type" "alu1")
6387    (set_attr "mode" "QI")])
6388
6389 (define_insn "*sub<mode>_2"
6390   [(set (reg FLAGS_REG)
6391         (compare
6392           (minus:SWI
6393             (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6394             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6395           (const_int 0)))
6396    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6397         (minus:SWI (match_dup 1) (match_dup 2)))]
6398   "ix86_match_ccmode (insn, CCGOCmode)
6399    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6400   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6401   [(set_attr "type" "alu")
6402    (set_attr "mode" "<MODE>")])
6403
6404 (define_insn "*subsi_2_zext"
6405   [(set (reg FLAGS_REG)
6406         (compare
6407           (minus:SI (match_operand:SI 1 "register_operand" "0")
6408                     (match_operand:SI 2 "x86_64_general_operand" "rme"))
6409           (const_int 0)))
6410    (set (match_operand:DI 0 "register_operand" "=r")
6411         (zero_extend:DI
6412           (minus:SI (match_dup 1)
6413                     (match_dup 2))))]
6414   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6415    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6416   "sub{l}\t{%2, %k0|%k0, %2}"
6417   [(set_attr "type" "alu")
6418    (set_attr "mode" "SI")])
6419
6420 (define_insn "*sub<mode>_3"
6421   [(set (reg FLAGS_REG)
6422         (compare (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6423                  (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6424    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6425         (minus:SWI (match_dup 1) (match_dup 2)))]
6426   "ix86_match_ccmode (insn, CCmode)
6427    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6428   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6429   [(set_attr "type" "alu")
6430    (set_attr "mode" "<MODE>")])
6431
6432 (define_insn "*subsi_3_zext"
6433   [(set (reg FLAGS_REG)
6434         (compare (match_operand:SI 1 "register_operand" "0")
6435                  (match_operand:SI 2 "x86_64_general_operand" "rme")))
6436    (set (match_operand:DI 0 "register_operand" "=r")
6437         (zero_extend:DI
6438           (minus:SI (match_dup 1)
6439                     (match_dup 2))))]
6440   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6441    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6442   "sub{l}\t{%2, %1|%1, %2}"
6443   [(set_attr "type" "alu")
6444    (set_attr "mode" "SI")])
6445 \f
6446 ;; Add with carry and subtract with borrow
6447
6448 (define_expand "<plusminus_insn><mode>3_carry"
6449   [(parallel
6450     [(set (match_operand:SWI 0 "nonimmediate_operand" "")
6451           (plusminus:SWI
6452             (match_operand:SWI 1 "nonimmediate_operand" "")
6453             (plus:SWI (match_operator:SWI 4 "ix86_carry_flag_operator"
6454                        [(match_operand 3 "flags_reg_operand" "")
6455                         (const_int 0)])
6456                       (match_operand:SWI 2 "<general_operand>" ""))))
6457      (clobber (reg:CC FLAGS_REG))])]
6458   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)")
6459
6460 (define_insn "*<plusminus_insn><mode>3_carry"
6461   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6462         (plusminus:SWI
6463           (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6464           (plus:SWI
6465             (match_operator 3 "ix86_carry_flag_operator"
6466              [(reg FLAGS_REG) (const_int 0)])
6467             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))))
6468    (clobber (reg:CC FLAGS_REG))]
6469   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
6470   "<plusminus_carry_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6471   [(set_attr "type" "alu")
6472    (set_attr "use_carry" "1")
6473    (set_attr "pent_pair" "pu")
6474    (set_attr "mode" "<MODE>")])
6475
6476 (define_insn "*addsi3_carry_zext"
6477   [(set (match_operand:DI 0 "register_operand" "=r")
6478         (zero_extend:DI
6479           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6480                    (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6481                              [(reg FLAGS_REG) (const_int 0)])
6482                             (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6483    (clobber (reg:CC FLAGS_REG))]
6484   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6485   "adc{l}\t{%2, %k0|%k0, %2}"
6486   [(set_attr "type" "alu")
6487    (set_attr "use_carry" "1")
6488    (set_attr "pent_pair" "pu")
6489    (set_attr "mode" "SI")])
6490
6491 (define_insn "*subsi3_carry_zext"
6492   [(set (match_operand:DI 0 "register_operand" "=r")
6493         (zero_extend:DI
6494           (minus:SI (match_operand:SI 1 "register_operand" "0")
6495                     (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6496                               [(reg FLAGS_REG) (const_int 0)])
6497                              (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6498    (clobber (reg:CC FLAGS_REG))]
6499   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6500   "sbb{l}\t{%2, %k0|%k0, %2}"
6501   [(set_attr "type" "alu")
6502    (set_attr "pent_pair" "pu")
6503    (set_attr "mode" "SI")])
6504 \f
6505 ;; Overflow setting add and subtract instructions
6506
6507 (define_insn "*add<mode>3_cconly_overflow"
6508   [(set (reg:CCC FLAGS_REG)
6509         (compare:CCC
6510           (plus:SWI
6511             (match_operand:SWI 1 "nonimmediate_operand" "%0")
6512             (match_operand:SWI 2 "<general_operand>" "<g>"))
6513           (match_dup 1)))
6514    (clobber (match_scratch:SWI 0 "=<r>"))]
6515   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6516   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
6517   [(set_attr "type" "alu")
6518    (set_attr "mode" "<MODE>")])
6519
6520 (define_insn "*sub<mode>3_cconly_overflow"
6521   [(set (reg:CCC FLAGS_REG)
6522         (compare:CCC
6523           (minus:SWI
6524             (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
6525             (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
6526           (match_dup 0)))]
6527   ""
6528   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
6529   [(set_attr "type" "icmp")
6530    (set_attr "mode" "<MODE>")])
6531
6532 (define_insn "*<plusminus_insn><mode>3_cc_overflow"
6533   [(set (reg:CCC FLAGS_REG)
6534         (compare:CCC
6535             (plusminus:SWI
6536                 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6537                 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6538             (match_dup 1)))
6539    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6540         (plusminus:SWI (match_dup 1) (match_dup 2)))]
6541   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6542   "<plusminus_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6543   [(set_attr "type" "alu")
6544    (set_attr "mode" "<MODE>")])
6545
6546 (define_insn "*<plusminus_insn>si3_zext_cc_overflow"
6547   [(set (reg:CCC FLAGS_REG)
6548         (compare:CCC
6549           (plusminus:SI
6550             (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
6551             (match_operand:SI 2 "x86_64_general_operand" "rme"))
6552           (match_dup 1)))
6553    (set (match_operand:DI 0 "register_operand" "=r")
6554         (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
6555   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
6556   "<plusminus_mnemonic>{l}\t{%2, %k0|%k0, %2}"
6557   [(set_attr "type" "alu")
6558    (set_attr "mode" "SI")])
6559
6560 ;; The patterns that match these are at the end of this file.
6561
6562 (define_expand "<plusminus_insn>xf3"
6563   [(set (match_operand:XF 0 "register_operand" "")
6564         (plusminus:XF
6565           (match_operand:XF 1 "register_operand" "")
6566           (match_operand:XF 2 "register_operand" "")))]
6567   "TARGET_80387")
6568
6569 (define_expand "<plusminus_insn><mode>3"
6570   [(set (match_operand:MODEF 0 "register_operand" "")
6571         (plusminus:MODEF
6572           (match_operand:MODEF 1 "register_operand" "")
6573           (match_operand:MODEF 2 "nonimmediate_operand" "")))]
6574   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
6575     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
6576 \f
6577 ;; Multiply instructions
6578
6579 (define_expand "mul<mode>3"
6580   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
6581                    (mult:SWIM248
6582                      (match_operand:SWIM248 1 "register_operand" "")
6583                      (match_operand:SWIM248 2 "<general_operand>" "")))
6584               (clobber (reg:CC FLAGS_REG))])])
6585
6586 (define_expand "mulqi3"
6587   [(parallel [(set (match_operand:QI 0 "register_operand" "")
6588                    (mult:QI
6589                      (match_operand:QI 1 "register_operand" "")
6590                      (match_operand:QI 2 "nonimmediate_operand" "")))
6591               (clobber (reg:CC FLAGS_REG))])]
6592   "TARGET_QIMODE_MATH")
6593
6594 ;; On AMDFAM10
6595 ;; IMUL reg32/64, reg32/64, imm8        Direct
6596 ;; IMUL reg32/64, mem32/64, imm8        VectorPath
6597 ;; IMUL reg32/64, reg32/64, imm32       Direct
6598 ;; IMUL reg32/64, mem32/64, imm32       VectorPath
6599 ;; IMUL reg32/64, reg32/64              Direct
6600 ;; IMUL reg32/64, mem32/64              Direct
6601 ;;
6602 ;; On BDVER1, all above IMULs use DirectPath
6603
6604 (define_insn "*mul<mode>3_1"
6605   [(set (match_operand:SWI48 0 "register_operand" "=r,r,r")
6606         (mult:SWI48
6607           (match_operand:SWI48 1 "nonimmediate_operand" "%rm,rm,0")
6608           (match_operand:SWI48 2 "<general_operand>" "K,<i>,mr")))
6609    (clobber (reg:CC FLAGS_REG))]
6610   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6611   "@
6612    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6613    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6614    imul{<imodesuffix>}\t{%2, %0|%0, %2}"
6615   [(set_attr "type" "imul")
6616    (set_attr "prefix_0f" "0,0,1")
6617    (set (attr "athlon_decode")
6618         (cond [(eq_attr "cpu" "athlon")
6619                   (const_string "vector")
6620                (eq_attr "alternative" "1")
6621                   (const_string "vector")
6622                (and (eq_attr "alternative" "2")
6623                     (match_operand 1 "memory_operand" ""))
6624                   (const_string "vector")]
6625               (const_string "direct")))
6626    (set (attr "amdfam10_decode")
6627         (cond [(and (eq_attr "alternative" "0,1")
6628                     (match_operand 1 "memory_operand" ""))
6629                   (const_string "vector")]
6630               (const_string "direct")))
6631    (set_attr "bdver1_decode" "direct")
6632    (set_attr "mode" "<MODE>")])
6633
6634 (define_insn "*mulsi3_1_zext"
6635   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6636         (zero_extend:DI
6637           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6638                    (match_operand:SI 2 "x86_64_general_operand" "K,e,mr"))))
6639    (clobber (reg:CC FLAGS_REG))]
6640   "TARGET_64BIT
6641    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6642   "@
6643    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6644    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6645    imul{l}\t{%2, %k0|%k0, %2}"
6646   [(set_attr "type" "imul")
6647    (set_attr "prefix_0f" "0,0,1")
6648    (set (attr "athlon_decode")
6649         (cond [(eq_attr "cpu" "athlon")
6650                   (const_string "vector")
6651                (eq_attr "alternative" "1")
6652                   (const_string "vector")
6653                (and (eq_attr "alternative" "2")
6654                     (match_operand 1 "memory_operand" ""))
6655                   (const_string "vector")]
6656               (const_string "direct")))
6657    (set (attr "amdfam10_decode")
6658         (cond [(and (eq_attr "alternative" "0,1")
6659                     (match_operand 1 "memory_operand" ""))
6660                   (const_string "vector")]
6661               (const_string "direct")))
6662    (set_attr "bdver1_decode" "direct")
6663    (set_attr "mode" "SI")])
6664
6665 ;; On AMDFAM10
6666 ;; IMUL reg16, reg16, imm8      VectorPath
6667 ;; IMUL reg16, mem16, imm8      VectorPath
6668 ;; IMUL reg16, reg16, imm16     VectorPath
6669 ;; IMUL reg16, mem16, imm16     VectorPath
6670 ;; IMUL reg16, reg16            Direct
6671 ;; IMUL reg16, mem16            Direct
6672 ;;
6673 ;; On BDVER1, all HI MULs use DoublePath
6674
6675 (define_insn "*mulhi3_1"
6676   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6677         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6678                  (match_operand:HI 2 "general_operand" "K,n,mr")))
6679    (clobber (reg:CC FLAGS_REG))]
6680   "TARGET_HIMODE_MATH
6681    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6682   "@
6683    imul{w}\t{%2, %1, %0|%0, %1, %2}
6684    imul{w}\t{%2, %1, %0|%0, %1, %2}
6685    imul{w}\t{%2, %0|%0, %2}"
6686   [(set_attr "type" "imul")
6687    (set_attr "prefix_0f" "0,0,1")
6688    (set (attr "athlon_decode")
6689         (cond [(eq_attr "cpu" "athlon")
6690                   (const_string "vector")
6691                (eq_attr "alternative" "1,2")
6692                   (const_string "vector")]
6693               (const_string "direct")))
6694    (set (attr "amdfam10_decode")
6695         (cond [(eq_attr "alternative" "0,1")
6696                   (const_string "vector")]
6697               (const_string "direct")))
6698    (set_attr "bdver1_decode" "double")
6699    (set_attr "mode" "HI")])
6700
6701 ;;On AMDFAM10 and BDVER1
6702 ;; MUL reg8     Direct
6703 ;; MUL mem8     Direct
6704
6705 (define_insn "*mulqi3_1"
6706   [(set (match_operand:QI 0 "register_operand" "=a")
6707         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6708                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
6709    (clobber (reg:CC FLAGS_REG))]
6710   "TARGET_QIMODE_MATH
6711    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6712   "mul{b}\t%2"
6713   [(set_attr "type" "imul")
6714    (set_attr "length_immediate" "0")
6715    (set (attr "athlon_decode")
6716      (if_then_else (eq_attr "cpu" "athlon")
6717         (const_string "vector")
6718         (const_string "direct")))
6719    (set_attr "amdfam10_decode" "direct")
6720    (set_attr "bdver1_decode" "direct")
6721    (set_attr "mode" "QI")])
6722
6723 (define_expand "<u>mul<mode><dwi>3"
6724   [(parallel [(set (match_operand:<DWI> 0 "register_operand" "")
6725                    (mult:<DWI>
6726                      (any_extend:<DWI>
6727                        (match_operand:DWIH 1 "nonimmediate_operand" ""))
6728                      (any_extend:<DWI>
6729                        (match_operand:DWIH 2 "register_operand" ""))))
6730               (clobber (reg:CC FLAGS_REG))])])
6731
6732 (define_expand "<u>mulqihi3"
6733   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6734                    (mult:HI
6735                      (any_extend:HI
6736                        (match_operand:QI 1 "nonimmediate_operand" ""))
6737                      (any_extend:HI
6738                        (match_operand:QI 2 "register_operand" ""))))
6739               (clobber (reg:CC FLAGS_REG))])]
6740   "TARGET_QIMODE_MATH")
6741
6742 (define_insn "*bmi2_umulditi3_1"
6743   [(set (match_operand:DI 0 "register_operand" "=r")
6744         (mult:DI
6745           (match_operand:DI 2 "nonimmediate_operand" "%d")
6746           (match_operand:DI 3 "nonimmediate_operand" "rm")))
6747    (set (match_operand:DI 1 "register_operand" "=r")
6748         (truncate:DI
6749           (lshiftrt:TI
6750             (mult:TI (zero_extend:TI (match_dup 2))
6751                      (zero_extend:TI (match_dup 3)))
6752             (const_int 64))))]
6753   "TARGET_64BIT && TARGET_BMI2
6754    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6755   "mulx\t{%3, %0, %1|%1, %0, %3}"
6756   [(set_attr "type" "imulx")
6757    (set_attr "prefix" "vex")
6758    (set_attr "mode" "DI")])
6759
6760 (define_insn "*bmi2_umulsidi3_1"
6761   [(set (match_operand:SI 0 "register_operand" "=r")
6762         (mult:SI
6763           (match_operand:SI 2 "nonimmediate_operand" "%d")
6764           (match_operand:SI 3 "nonimmediate_operand" "rm")))
6765    (set (match_operand:SI 1 "register_operand" "=r")
6766         (truncate:SI
6767           (lshiftrt:DI
6768             (mult:DI (zero_extend:DI (match_dup 2))
6769                      (zero_extend:DI (match_dup 3)))
6770             (const_int 32))))]
6771   "!TARGET_64BIT && TARGET_BMI2
6772    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6773   "mulx\t{%3, %0, %1|%1, %0, %3}"
6774   [(set_attr "type" "imulx")
6775    (set_attr "prefix" "vex")
6776    (set_attr "mode" "SI")])
6777
6778 (define_insn "*umul<mode><dwi>3_1"
6779   [(set (match_operand:<DWI> 0 "register_operand" "=A,r")
6780         (mult:<DWI>
6781           (zero_extend:<DWI>
6782             (match_operand:DWIH 1 "nonimmediate_operand" "%0,d"))
6783           (zero_extend:<DWI>
6784             (match_operand:DWIH 2 "nonimmediate_operand" "rm,rm"))))
6785    (clobber (reg:CC FLAGS_REG))]
6786   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6787   "@
6788    mul{<imodesuffix>}\t%2
6789    #"
6790   [(set_attr "isa" "*,bmi2")
6791    (set_attr "type" "imul,imulx")
6792    (set_attr "length_immediate" "0,*")
6793    (set (attr "athlon_decode")
6794         (cond [(eq_attr "alternative" "0")
6795                  (if_then_else (eq_attr "cpu" "athlon")
6796                    (const_string "vector")
6797                    (const_string "double"))]
6798               (const_string "*")))
6799    (set_attr "amdfam10_decode" "double,*")
6800    (set_attr "bdver1_decode" "direct,*")
6801    (set_attr "prefix" "orig,vex")
6802    (set_attr "mode" "<MODE>")])
6803
6804 ;; Convert mul to the mulx pattern to avoid flags dependency.
6805 (define_split
6806  [(set (match_operand:<DWI> 0 "register_operand" "")
6807        (mult:<DWI>
6808          (zero_extend:<DWI>
6809            (match_operand:DWIH 1 "register_operand" ""))
6810          (zero_extend:<DWI>
6811            (match_operand:DWIH 2 "nonimmediate_operand" ""))))
6812   (clobber (reg:CC FLAGS_REG))]
6813  "TARGET_BMI2 && reload_completed
6814   && true_regnum (operands[1]) == DX_REG"
6815   [(parallel [(set (match_dup 3)
6816                    (mult:DWIH (match_dup 1) (match_dup 2)))
6817               (set (match_dup 4)
6818                    (truncate:DWIH
6819                      (lshiftrt:<DWI>
6820                        (mult:<DWI> (zero_extend:<DWI> (match_dup 1))
6821                                    (zero_extend:<DWI> (match_dup 2)))
6822                        (match_dup 5))))])]
6823 {
6824   split_double_mode (<DWI>mode, &operands[0], 1, &operands[3], &operands[4]);
6825
6826   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
6827 })
6828
6829 (define_insn "*mul<mode><dwi>3_1"
6830   [(set (match_operand:<DWI> 0 "register_operand" "=A")
6831         (mult:<DWI>
6832           (sign_extend:<DWI>
6833             (match_operand:DWIH 1 "nonimmediate_operand" "%0"))
6834           (sign_extend:<DWI>
6835             (match_operand:DWIH 2 "nonimmediate_operand" "rm"))))
6836    (clobber (reg:CC FLAGS_REG))]
6837   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6838   "imul{<imodesuffix>}\t%2"
6839   [(set_attr "type" "imul")
6840    (set_attr "length_immediate" "0")
6841    (set (attr "athlon_decode")
6842      (if_then_else (eq_attr "cpu" "athlon")
6843         (const_string "vector")
6844         (const_string "double")))
6845    (set_attr "amdfam10_decode" "double")
6846    (set_attr "bdver1_decode" "direct")
6847    (set_attr "mode" "<MODE>")])
6848
6849 (define_insn "*<u>mulqihi3_1"
6850   [(set (match_operand:HI 0 "register_operand" "=a")
6851         (mult:HI
6852           (any_extend:HI
6853             (match_operand:QI 1 "nonimmediate_operand" "%0"))
6854           (any_extend:HI
6855             (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6856    (clobber (reg:CC FLAGS_REG))]
6857   "TARGET_QIMODE_MATH
6858    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6859   "<sgnprefix>mul{b}\t%2"
6860   [(set_attr "type" "imul")
6861    (set_attr "length_immediate" "0")
6862    (set (attr "athlon_decode")
6863      (if_then_else (eq_attr "cpu" "athlon")
6864         (const_string "vector")
6865         (const_string "direct")))
6866    (set_attr "amdfam10_decode" "direct")
6867    (set_attr "bdver1_decode" "direct")
6868    (set_attr "mode" "QI")])
6869
6870 (define_expand "<s>mul<mode>3_highpart"
6871   [(parallel [(set (match_operand:SWI48 0 "register_operand" "")
6872                    (truncate:SWI48
6873                      (lshiftrt:<DWI>
6874                        (mult:<DWI>
6875                          (any_extend:<DWI>
6876                            (match_operand:SWI48 1 "nonimmediate_operand" ""))
6877                          (any_extend:<DWI>
6878                            (match_operand:SWI48 2 "register_operand" "")))
6879                        (match_dup 4))))
6880               (clobber (match_scratch:SWI48 3 ""))
6881               (clobber (reg:CC FLAGS_REG))])]
6882   ""
6883   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
6884
6885 (define_insn "*<s>muldi3_highpart_1"
6886   [(set (match_operand:DI 0 "register_operand" "=d")
6887         (truncate:DI
6888           (lshiftrt:TI
6889             (mult:TI
6890               (any_extend:TI
6891                 (match_operand:DI 1 "nonimmediate_operand" "%a"))
6892               (any_extend:TI
6893                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
6894             (const_int 64))))
6895    (clobber (match_scratch:DI 3 "=1"))
6896    (clobber (reg:CC FLAGS_REG))]
6897   "TARGET_64BIT
6898    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6899   "<sgnprefix>mul{q}\t%2"
6900   [(set_attr "type" "imul")
6901    (set_attr "length_immediate" "0")
6902    (set (attr "athlon_decode")
6903      (if_then_else (eq_attr "cpu" "athlon")
6904         (const_string "vector")
6905         (const_string "double")))
6906    (set_attr "amdfam10_decode" "double")
6907    (set_attr "bdver1_decode" "direct")
6908    (set_attr "mode" "DI")])
6909
6910 (define_insn "*<s>mulsi3_highpart_1"
6911   [(set (match_operand:SI 0 "register_operand" "=d")
6912         (truncate:SI
6913           (lshiftrt:DI
6914             (mult:DI
6915               (any_extend:DI
6916                 (match_operand:SI 1 "nonimmediate_operand" "%a"))
6917               (any_extend:DI
6918                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6919             (const_int 32))))
6920    (clobber (match_scratch:SI 3 "=1"))
6921    (clobber (reg:CC FLAGS_REG))]
6922   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6923   "<sgnprefix>mul{l}\t%2"
6924   [(set_attr "type" "imul")
6925    (set_attr "length_immediate" "0")
6926    (set (attr "athlon_decode")
6927      (if_then_else (eq_attr "cpu" "athlon")
6928         (const_string "vector")
6929         (const_string "double")))
6930    (set_attr "amdfam10_decode" "double")
6931    (set_attr "bdver1_decode" "direct")
6932    (set_attr "mode" "SI")])
6933
6934 (define_insn "*<s>mulsi3_highpart_zext"
6935   [(set (match_operand:DI 0 "register_operand" "=d")
6936         (zero_extend:DI (truncate:SI
6937           (lshiftrt:DI
6938             (mult:DI (any_extend:DI
6939                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
6940                      (any_extend:DI
6941                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
6942             (const_int 32)))))
6943    (clobber (match_scratch:SI 3 "=1"))
6944    (clobber (reg:CC FLAGS_REG))]
6945   "TARGET_64BIT
6946    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6947   "<sgnprefix>mul{l}\t%2"
6948   [(set_attr "type" "imul")
6949    (set_attr "length_immediate" "0")
6950    (set (attr "athlon_decode")
6951      (if_then_else (eq_attr "cpu" "athlon")
6952         (const_string "vector")
6953         (const_string "double")))
6954    (set_attr "amdfam10_decode" "double")
6955    (set_attr "bdver1_decode" "direct")
6956    (set_attr "mode" "SI")])
6957
6958 ;; The patterns that match these are at the end of this file.
6959
6960 (define_expand "mulxf3"
6961   [(set (match_operand:XF 0 "register_operand" "")
6962         (mult:XF (match_operand:XF 1 "register_operand" "")
6963                  (match_operand:XF 2 "register_operand" "")))]
6964   "TARGET_80387")
6965
6966 (define_expand "mul<mode>3"
6967   [(set (match_operand:MODEF 0 "register_operand" "")
6968         (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
6969                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
6970   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
6971     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
6972 \f
6973 ;; Divide instructions
6974
6975 ;; The patterns that match these are at the end of this file.
6976
6977 (define_expand "divxf3"
6978   [(set (match_operand:XF 0 "register_operand" "")
6979         (div:XF (match_operand:XF 1 "register_operand" "")
6980                 (match_operand:XF 2 "register_operand" "")))]
6981   "TARGET_80387")
6982
6983 (define_expand "divdf3"
6984   [(set (match_operand:DF 0 "register_operand" "")
6985         (div:DF (match_operand:DF 1 "register_operand" "")
6986                 (match_operand:DF 2 "nonimmediate_operand" "")))]
6987    "(TARGET_80387 && X87_ENABLE_ARITH (DFmode))
6988     || (TARGET_SSE2 && TARGET_SSE_MATH)")
6989
6990 (define_expand "divsf3"
6991   [(set (match_operand:SF 0 "register_operand" "")
6992         (div:SF (match_operand:SF 1 "register_operand" "")
6993                 (match_operand:SF 2 "nonimmediate_operand" "")))]
6994   "(TARGET_80387 && X87_ENABLE_ARITH (SFmode))
6995     || TARGET_SSE_MATH"
6996 {
6997   if (TARGET_SSE_MATH
6998       && TARGET_RECIP_DIV
6999       && optimize_insn_for_speed_p ()
7000       && flag_finite_math_only && !flag_trapping_math
7001       && flag_unsafe_math_optimizations)
7002     {
7003       ix86_emit_swdivsf (operands[0], operands[1],
7004                          operands[2], SFmode);
7005       DONE;
7006     }
7007 })
7008 \f
7009 ;; Divmod instructions.
7010
7011 (define_expand "divmod<mode>4"
7012   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7013                    (div:SWIM248
7014                      (match_operand:SWIM248 1 "register_operand" "")
7015                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7016               (set (match_operand:SWIM248 3 "register_operand" "")
7017                    (mod:SWIM248 (match_dup 1) (match_dup 2)))
7018               (clobber (reg:CC FLAGS_REG))])])
7019
7020 ;; Split with 8bit unsigned divide:
7021 ;;      if (dividend an divisor are in [0-255])
7022 ;;         use 8bit unsigned integer divide
7023 ;;       else
7024 ;;         use original integer divide
7025 (define_split
7026   [(set (match_operand:SWI48 0 "register_operand" "")
7027         (div:SWI48 (match_operand:SWI48 2 "register_operand" "")
7028                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7029    (set (match_operand:SWI48 1 "register_operand" "")
7030         (mod:SWI48 (match_dup 2) (match_dup 3)))
7031    (clobber (reg:CC FLAGS_REG))]
7032   "TARGET_USE_8BIT_IDIV
7033    && TARGET_QIMODE_MATH
7034    && can_create_pseudo_p ()
7035    && !optimize_insn_for_size_p ()"
7036   [(const_int 0)]
7037   "ix86_split_idivmod (<MODE>mode, operands, true); DONE;")
7038
7039 (define_insn_and_split "divmod<mode>4_1"
7040   [(set (match_operand:SWI48 0 "register_operand" "=a")
7041         (div:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7042                    (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7043    (set (match_operand:SWI48 1 "register_operand" "=&d")
7044         (mod:SWI48 (match_dup 2) (match_dup 3)))
7045    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7046    (clobber (reg:CC FLAGS_REG))]
7047   ""
7048   "#"
7049   "reload_completed"
7050   [(parallel [(set (match_dup 1)
7051                    (ashiftrt:SWI48 (match_dup 4) (match_dup 5)))
7052               (clobber (reg:CC FLAGS_REG))])
7053    (parallel [(set (match_dup 0)
7054                    (div:SWI48 (match_dup 2) (match_dup 3)))
7055               (set (match_dup 1)
7056                    (mod:SWI48 (match_dup 2) (match_dup 3)))
7057               (use (match_dup 1))
7058               (clobber (reg:CC FLAGS_REG))])]
7059 {
7060   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7061
7062   if (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
7063     operands[4] = operands[2];
7064   else
7065     {
7066       /* Avoid use of cltd in favor of a mov+shift.  */
7067       emit_move_insn (operands[1], operands[2]);
7068       operands[4] = operands[1];
7069     }
7070 }
7071   [(set_attr "type" "multi")
7072    (set_attr "mode" "<MODE>")])
7073
7074 (define_insn_and_split "*divmod<mode>4"
7075   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7076         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7077                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7078    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7079         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7080    (clobber (reg:CC FLAGS_REG))]
7081   ""
7082   "#"
7083   "reload_completed"
7084   [(parallel [(set (match_dup 1)
7085                    (ashiftrt:SWIM248 (match_dup 4) (match_dup 5)))
7086               (clobber (reg:CC FLAGS_REG))])
7087    (parallel [(set (match_dup 0)
7088                    (div:SWIM248 (match_dup 2) (match_dup 3)))
7089               (set (match_dup 1)
7090                    (mod:SWIM248 (match_dup 2) (match_dup 3)))
7091               (use (match_dup 1))
7092               (clobber (reg:CC FLAGS_REG))])]
7093 {
7094   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7095
7096   if (<MODE>mode != HImode
7097       && (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD))
7098     operands[4] = operands[2];
7099   else
7100     {
7101       /* Avoid use of cltd in favor of a mov+shift.  */
7102       emit_move_insn (operands[1], operands[2]);
7103       operands[4] = operands[1];
7104     }
7105 }
7106   [(set_attr "type" "multi")
7107    (set_attr "mode" "<MODE>")])
7108
7109 (define_insn "*divmod<mode>4_noext"
7110   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7111         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7112                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7113    (set (match_operand:SWIM248 1 "register_operand" "=d")
7114         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7115    (use (match_operand:SWIM248 4 "register_operand" "1"))
7116    (clobber (reg:CC FLAGS_REG))]
7117   ""
7118   "idiv{<imodesuffix>}\t%3"
7119   [(set_attr "type" "idiv")
7120    (set_attr "mode" "<MODE>")])
7121
7122 (define_expand "divmodqi4"
7123   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7124                    (div:QI
7125                      (match_operand:QI 1 "register_operand" "")
7126                      (match_operand:QI 2 "nonimmediate_operand" "")))
7127               (set (match_operand:QI 3 "register_operand" "")
7128                    (mod:QI (match_dup 1) (match_dup 2)))
7129               (clobber (reg:CC FLAGS_REG))])]
7130   "TARGET_QIMODE_MATH"
7131 {
7132   rtx div, mod, insn;
7133   rtx tmp0, tmp1;
7134   
7135   tmp0 = gen_reg_rtx (HImode);
7136   tmp1 = gen_reg_rtx (HImode);
7137
7138   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7139      in AX.  */
7140   emit_insn (gen_extendqihi2 (tmp1, operands[1]));
7141   emit_insn (gen_divmodhiqi3 (tmp0, tmp1, operands[2]));
7142
7143   /* Extract remainder from AH.  */
7144   tmp1 = gen_rtx_SIGN_EXTRACT (QImode, tmp0, GEN_INT (8), GEN_INT (8));
7145   insn = emit_move_insn (operands[3], tmp1);
7146
7147   mod = gen_rtx_MOD (QImode, operands[1], operands[2]);
7148   set_unique_reg_note (insn, REG_EQUAL, mod);
7149
7150   /* Extract quotient from AL.  */
7151   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7152
7153   div = gen_rtx_DIV (QImode, operands[1], operands[2]);
7154   set_unique_reg_note (insn, REG_EQUAL, div);
7155
7156   DONE;
7157 })
7158
7159 ;; Divide AX by r/m8, with result stored in
7160 ;; AL <- Quotient
7161 ;; AH <- Remainder
7162 ;; Change div/mod to HImode and extend the second argument to HImode
7163 ;; so that mode of div/mod matches with mode of arguments.  Otherwise
7164 ;; combine may fail.
7165 (define_insn "divmodhiqi3"
7166   [(set (match_operand:HI 0 "register_operand" "=a")
7167         (ior:HI
7168           (ashift:HI
7169             (zero_extend:HI
7170               (truncate:QI
7171                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7172                         (sign_extend:HI
7173                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7174             (const_int 8))
7175           (zero_extend:HI
7176             (truncate:QI
7177               (div:HI (match_dup 1) (sign_extend:HI (match_dup 2)))))))
7178    (clobber (reg:CC FLAGS_REG))]
7179   "TARGET_QIMODE_MATH"
7180   "idiv{b}\t%2"
7181   [(set_attr "type" "idiv")
7182    (set_attr "mode" "QI")])
7183
7184 (define_expand "udivmod<mode>4"
7185   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7186                    (udiv:SWIM248
7187                      (match_operand:SWIM248 1 "register_operand" "")
7188                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7189               (set (match_operand:SWIM248 3 "register_operand" "")
7190                    (umod:SWIM248 (match_dup 1) (match_dup 2)))
7191               (clobber (reg:CC FLAGS_REG))])])
7192
7193 ;; Split with 8bit unsigned divide:
7194 ;;      if (dividend an divisor are in [0-255])
7195 ;;         use 8bit unsigned integer divide
7196 ;;       else
7197 ;;         use original integer divide
7198 (define_split
7199   [(set (match_operand:SWI48 0 "register_operand" "")
7200         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "")
7201                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7202    (set (match_operand:SWI48 1 "register_operand" "")
7203         (umod:SWI48 (match_dup 2) (match_dup 3)))
7204    (clobber (reg:CC FLAGS_REG))]
7205   "TARGET_USE_8BIT_IDIV
7206    && TARGET_QIMODE_MATH
7207    && can_create_pseudo_p ()
7208    && !optimize_insn_for_size_p ()"
7209   [(const_int 0)]
7210   "ix86_split_idivmod (<MODE>mode, operands, false); DONE;")
7211
7212 (define_insn_and_split "udivmod<mode>4_1"
7213   [(set (match_operand:SWI48 0 "register_operand" "=a")
7214         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7215                     (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7216    (set (match_operand:SWI48 1 "register_operand" "=&d")
7217         (umod:SWI48 (match_dup 2) (match_dup 3)))
7218    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7219    (clobber (reg:CC FLAGS_REG))]
7220   ""
7221   "#"
7222   "reload_completed"
7223   [(set (match_dup 1) (const_int 0))
7224    (parallel [(set (match_dup 0)
7225                    (udiv:SWI48 (match_dup 2) (match_dup 3)))
7226               (set (match_dup 1)
7227                    (umod:SWI48 (match_dup 2) (match_dup 3)))
7228               (use (match_dup 1))
7229               (clobber (reg:CC FLAGS_REG))])]
7230   ""
7231   [(set_attr "type" "multi")
7232    (set_attr "mode" "<MODE>")])
7233
7234 (define_insn_and_split "*udivmod<mode>4"
7235   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7236         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7237                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7238    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7239         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7240    (clobber (reg:CC FLAGS_REG))]
7241   ""
7242   "#"
7243   "reload_completed"
7244   [(set (match_dup 1) (const_int 0))
7245    (parallel [(set (match_dup 0)
7246                    (udiv:SWIM248 (match_dup 2) (match_dup 3)))
7247               (set (match_dup 1)
7248                    (umod:SWIM248 (match_dup 2) (match_dup 3)))
7249               (use (match_dup 1))
7250               (clobber (reg:CC FLAGS_REG))])]
7251   ""
7252   [(set_attr "type" "multi")
7253    (set_attr "mode" "<MODE>")])
7254
7255 (define_insn "*udivmod<mode>4_noext"
7256   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7257         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7258                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7259    (set (match_operand:SWIM248 1 "register_operand" "=d")
7260         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7261    (use (match_operand:SWIM248 4 "register_operand" "1"))
7262    (clobber (reg:CC FLAGS_REG))]
7263   ""
7264   "div{<imodesuffix>}\t%3"
7265   [(set_attr "type" "idiv")
7266    (set_attr "mode" "<MODE>")])
7267
7268 (define_expand "udivmodqi4"
7269   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7270                    (udiv:QI
7271                      (match_operand:QI 1 "register_operand" "")
7272                      (match_operand:QI 2 "nonimmediate_operand" "")))
7273               (set (match_operand:QI 3 "register_operand" "")
7274                    (umod:QI (match_dup 1) (match_dup 2)))
7275               (clobber (reg:CC FLAGS_REG))])]
7276   "TARGET_QIMODE_MATH"
7277 {
7278   rtx div, mod, insn;
7279   rtx tmp0, tmp1;
7280   
7281   tmp0 = gen_reg_rtx (HImode);
7282   tmp1 = gen_reg_rtx (HImode);
7283
7284   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7285      in AX.  */
7286   emit_insn (gen_zero_extendqihi2 (tmp1, operands[1]));
7287   emit_insn (gen_udivmodhiqi3 (tmp0, tmp1, operands[2]));
7288
7289   /* Extract remainder from AH.  */
7290   tmp1 = gen_rtx_ZERO_EXTRACT (SImode, tmp0, GEN_INT (8), GEN_INT (8));
7291   tmp1 = simplify_gen_subreg (QImode, tmp1, SImode, 0);
7292   insn = emit_move_insn (operands[3], tmp1);
7293
7294   mod = gen_rtx_UMOD (QImode, operands[1], operands[2]);
7295   set_unique_reg_note (insn, REG_EQUAL, mod);
7296
7297   /* Extract quotient from AL.  */
7298   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7299
7300   div = gen_rtx_UDIV (QImode, operands[1], operands[2]);
7301   set_unique_reg_note (insn, REG_EQUAL, div);
7302
7303   DONE;
7304 })
7305
7306 (define_insn "udivmodhiqi3"
7307   [(set (match_operand:HI 0 "register_operand" "=a")
7308         (ior:HI
7309           (ashift:HI
7310             (zero_extend:HI
7311               (truncate:QI
7312                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7313                         (zero_extend:HI
7314                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7315             (const_int 8))
7316           (zero_extend:HI
7317             (truncate:QI
7318               (div:HI (match_dup 1) (zero_extend:HI (match_dup 2)))))))
7319    (clobber (reg:CC FLAGS_REG))]
7320   "TARGET_QIMODE_MATH"
7321   "div{b}\t%2"
7322   [(set_attr "type" "idiv")
7323    (set_attr "mode" "QI")])
7324
7325 ;; We cannot use div/idiv for double division, because it causes
7326 ;; "division by zero" on the overflow and that's not what we expect
7327 ;; from truncate.  Because true (non truncating) double division is
7328 ;; never generated, we can't create this insn anyway.
7329 ;
7330 ;(define_insn ""
7331 ;  [(set (match_operand:SI 0 "register_operand" "=a")
7332 ;       (truncate:SI
7333 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
7334 ;                  (zero_extend:DI
7335 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7336 ;   (set (match_operand:SI 3 "register_operand" "=d")
7337 ;       (truncate:SI
7338 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7339 ;   (clobber (reg:CC FLAGS_REG))]
7340 ;  ""
7341 ;  "div{l}\t{%2, %0|%0, %2}"
7342 ;  [(set_attr "type" "idiv")])
7343 \f
7344 ;;- Logical AND instructions
7345
7346 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7347 ;; Note that this excludes ah.
7348
7349 (define_expand "testsi_ccno_1"
7350   [(set (reg:CCNO FLAGS_REG)
7351         (compare:CCNO
7352           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7353                   (match_operand:SI 1 "x86_64_nonmemory_operand" ""))
7354           (const_int 0)))])
7355
7356 (define_expand "testqi_ccz_1"
7357   [(set (reg:CCZ FLAGS_REG)
7358         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7359                              (match_operand:QI 1 "nonmemory_operand" ""))
7360                  (const_int 0)))])
7361
7362 (define_expand "testdi_ccno_1"
7363   [(set (reg:CCNO FLAGS_REG)
7364         (compare:CCNO
7365           (and:DI (match_operand:DI 0 "nonimmediate_operand" "")
7366                   (match_operand:DI 1 "x86_64_szext_general_operand" ""))
7367           (const_int 0)))]
7368   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))")
7369
7370 (define_insn "*testdi_1"
7371   [(set (reg FLAGS_REG)
7372         (compare
7373          (and:DI
7374           (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7375           (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7376          (const_int 0)))]
7377   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7378    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7379   "@
7380    test{l}\t{%k1, %k0|%k0, %k1}
7381    test{l}\t{%k1, %k0|%k0, %k1}
7382    test{q}\t{%1, %0|%0, %1}
7383    test{q}\t{%1, %0|%0, %1}
7384    test{q}\t{%1, %0|%0, %1}"
7385   [(set_attr "type" "test")
7386    (set_attr "modrm" "0,1,0,1,1")
7387    (set_attr "mode" "SI,SI,DI,DI,DI")])
7388
7389 (define_insn "*testqi_1_maybe_si"
7390   [(set (reg FLAGS_REG)
7391         (compare
7392           (and:QI
7393             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7394             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7395           (const_int 0)))]
7396    "!(MEM_P (operands[0]) && MEM_P (operands[1]))
7397     && ix86_match_ccmode (insn,
7398                          CONST_INT_P (operands[1])
7399                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7400 {
7401   if (which_alternative == 3)
7402     {
7403       if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
7404         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7405       return "test{l}\t{%1, %k0|%k0, %1}";
7406     }
7407   return "test{b}\t{%1, %0|%0, %1}";
7408 }
7409   [(set_attr "type" "test")
7410    (set_attr "modrm" "0,1,1,1")
7411    (set_attr "mode" "QI,QI,QI,SI")
7412    (set_attr "pent_pair" "uv,np,uv,np")])
7413
7414 (define_insn "*test<mode>_1"
7415   [(set (reg FLAGS_REG)
7416         (compare
7417          (and:SWI124
7418           (match_operand:SWI124 0 "nonimmediate_operand" "%!*a,<r>,<r>m")
7419           (match_operand:SWI124 1 "<general_operand>" "<i>,<i>,<r><i>"))
7420          (const_int 0)))]
7421   "ix86_match_ccmode (insn, CCNOmode)
7422    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7423   "test{<imodesuffix>}\t{%1, %0|%0, %1}"
7424   [(set_attr "type" "test")
7425    (set_attr "modrm" "0,1,1")
7426    (set_attr "mode" "<MODE>")
7427    (set_attr "pent_pair" "uv,np,uv")])
7428
7429 (define_expand "testqi_ext_ccno_0"
7430   [(set (reg:CCNO FLAGS_REG)
7431         (compare:CCNO
7432           (and:SI
7433             (zero_extract:SI
7434               (match_operand 0 "ext_register_operand" "")
7435               (const_int 8)
7436               (const_int 8))
7437             (match_operand 1 "const_int_operand" ""))
7438           (const_int 0)))])
7439
7440 (define_insn "*testqi_ext_0"
7441   [(set (reg FLAGS_REG)
7442         (compare
7443           (and:SI
7444             (zero_extract:SI
7445               (match_operand 0 "ext_register_operand" "Q")
7446               (const_int 8)
7447               (const_int 8))
7448             (match_operand 1 "const_int_operand" "n"))
7449           (const_int 0)))]
7450   "ix86_match_ccmode (insn, CCNOmode)"
7451   "test{b}\t{%1, %h0|%h0, %1}"
7452   [(set_attr "type" "test")
7453    (set_attr "mode" "QI")
7454    (set_attr "length_immediate" "1")
7455    (set_attr "modrm" "1")
7456    (set_attr "pent_pair" "np")])
7457
7458 (define_insn "*testqi_ext_1_rex64"
7459   [(set (reg FLAGS_REG)
7460         (compare
7461           (and:SI
7462             (zero_extract:SI
7463               (match_operand 0 "ext_register_operand" "Q")
7464               (const_int 8)
7465               (const_int 8))
7466             (zero_extend:SI
7467               (match_operand:QI 1 "register_operand" "Q")))
7468           (const_int 0)))]
7469   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7470   "test{b}\t{%1, %h0|%h0, %1}"
7471   [(set_attr "type" "test")
7472    (set_attr "mode" "QI")])
7473
7474 (define_insn "*testqi_ext_1"
7475   [(set (reg FLAGS_REG)
7476         (compare
7477           (and:SI
7478             (zero_extract:SI
7479               (match_operand 0 "ext_register_operand" "Q")
7480               (const_int 8)
7481               (const_int 8))
7482             (zero_extend:SI
7483               (match_operand:QI 1 "general_operand" "Qm")))
7484           (const_int 0)))]
7485   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7486   "test{b}\t{%1, %h0|%h0, %1}"
7487   [(set_attr "type" "test")
7488    (set_attr "mode" "QI")])
7489
7490 (define_insn "*testqi_ext_2"
7491   [(set (reg FLAGS_REG)
7492         (compare
7493           (and:SI
7494             (zero_extract:SI
7495               (match_operand 0 "ext_register_operand" "Q")
7496               (const_int 8)
7497               (const_int 8))
7498             (zero_extract:SI
7499               (match_operand 1 "ext_register_operand" "Q")
7500               (const_int 8)
7501               (const_int 8)))
7502           (const_int 0)))]
7503   "ix86_match_ccmode (insn, CCNOmode)"
7504   "test{b}\t{%h1, %h0|%h0, %h1}"
7505   [(set_attr "type" "test")
7506    (set_attr "mode" "QI")])
7507
7508 (define_insn "*testqi_ext_3_rex64"
7509   [(set (reg FLAGS_REG)
7510         (compare (zero_extract:DI
7511                    (match_operand 0 "nonimmediate_operand" "rm")
7512                    (match_operand:DI 1 "const_int_operand" "")
7513                    (match_operand:DI 2 "const_int_operand" ""))
7514                  (const_int 0)))]
7515   "TARGET_64BIT
7516    && ix86_match_ccmode (insn, CCNOmode)
7517    && INTVAL (operands[1]) > 0
7518    && INTVAL (operands[2]) >= 0
7519    /* Ensure that resulting mask is zero or sign extended operand.  */
7520    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7521        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7522            && INTVAL (operands[1]) > 32))
7523    && (GET_MODE (operands[0]) == SImode
7524        || GET_MODE (operands[0]) == DImode
7525        || GET_MODE (operands[0]) == HImode
7526        || GET_MODE (operands[0]) == QImode)"
7527   "#")
7528
7529 ;; Combine likes to form bit extractions for some tests.  Humor it.
7530 (define_insn "*testqi_ext_3"
7531   [(set (reg FLAGS_REG)
7532         (compare (zero_extract:SI
7533                    (match_operand 0 "nonimmediate_operand" "rm")
7534                    (match_operand:SI 1 "const_int_operand" "")
7535                    (match_operand:SI 2 "const_int_operand" ""))
7536                  (const_int 0)))]
7537   "ix86_match_ccmode (insn, CCNOmode)
7538    && INTVAL (operands[1]) > 0
7539    && INTVAL (operands[2]) >= 0
7540    && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7541    && (GET_MODE (operands[0]) == SImode
7542        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7543        || GET_MODE (operands[0]) == HImode
7544        || GET_MODE (operands[0]) == QImode)"
7545   "#")
7546
7547 (define_split
7548   [(set (match_operand 0 "flags_reg_operand" "")
7549         (match_operator 1 "compare_operator"
7550           [(zero_extract
7551              (match_operand 2 "nonimmediate_operand" "")
7552              (match_operand 3 "const_int_operand" "")
7553              (match_operand 4 "const_int_operand" ""))
7554            (const_int 0)]))]
7555   "ix86_match_ccmode (insn, CCNOmode)"
7556   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7557 {
7558   rtx val = operands[2];
7559   HOST_WIDE_INT len = INTVAL (operands[3]);
7560   HOST_WIDE_INT pos = INTVAL (operands[4]);
7561   HOST_WIDE_INT mask;
7562   enum machine_mode mode, submode;
7563
7564   mode = GET_MODE (val);
7565   if (MEM_P (val))
7566     {
7567       /* ??? Combine likes to put non-volatile mem extractions in QImode
7568          no matter the size of the test.  So find a mode that works.  */
7569       if (! MEM_VOLATILE_P (val))
7570         {
7571           mode = smallest_mode_for_size (pos + len, MODE_INT);
7572           val = adjust_address (val, mode, 0);
7573         }
7574     }
7575   else if (GET_CODE (val) == SUBREG
7576            && (submode = GET_MODE (SUBREG_REG (val)),
7577                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7578            && pos + len <= GET_MODE_BITSIZE (submode)
7579            && GET_MODE_CLASS (submode) == MODE_INT)
7580     {
7581       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
7582       mode = submode;
7583       val = SUBREG_REG (val);
7584     }
7585   else if (mode == HImode && pos + len <= 8)
7586     {
7587       /* Small HImode tests can be converted to QImode.  */
7588       mode = QImode;
7589       val = gen_lowpart (QImode, val);
7590     }
7591
7592   if (len == HOST_BITS_PER_WIDE_INT)
7593     mask = -1;
7594   else
7595     mask = ((HOST_WIDE_INT)1 << len) - 1;
7596   mask <<= pos;
7597
7598   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7599 })
7600
7601 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7602 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7603 ;; this is relatively important trick.
7604 ;; Do the conversion only post-reload to avoid limiting of the register class
7605 ;; to QI regs.
7606 (define_split
7607   [(set (match_operand 0 "flags_reg_operand" "")
7608         (match_operator 1 "compare_operator"
7609           [(and (match_operand 2 "register_operand" "")
7610                 (match_operand 3 "const_int_operand" ""))
7611            (const_int 0)]))]
7612    "reload_completed
7613     && QI_REG_P (operands[2])
7614     && GET_MODE (operands[2]) != QImode
7615     && ((ix86_match_ccmode (insn, CCZmode)
7616          && !(INTVAL (operands[3]) & ~(255 << 8)))
7617         || (ix86_match_ccmode (insn, CCNOmode)
7618             && !(INTVAL (operands[3]) & ~(127 << 8))))"
7619   [(set (match_dup 0)
7620         (match_op_dup 1
7621           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7622                    (match_dup 3))
7623            (const_int 0)]))]
7624 {
7625   operands[2] = gen_lowpart (SImode, operands[2]);
7626   operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);
7627 })
7628
7629 (define_split
7630   [(set (match_operand 0 "flags_reg_operand" "")
7631         (match_operator 1 "compare_operator"
7632           [(and (match_operand 2 "nonimmediate_operand" "")
7633                 (match_operand 3 "const_int_operand" ""))
7634            (const_int 0)]))]
7635    "reload_completed
7636     && GET_MODE (operands[2]) != QImode
7637     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7638     && ((ix86_match_ccmode (insn, CCZmode)
7639          && !(INTVAL (operands[3]) & ~255))
7640         || (ix86_match_ccmode (insn, CCNOmode)
7641             && !(INTVAL (operands[3]) & ~127)))"
7642   [(set (match_dup 0)
7643         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7644                          (const_int 0)]))]
7645 {
7646   operands[2] = gen_lowpart (QImode, operands[2]);
7647   operands[3] = gen_lowpart (QImode, operands[3]);
7648 })
7649
7650 ;; %%% This used to optimize known byte-wide and operations to memory,
7651 ;; and sometimes to QImode registers.  If this is considered useful,
7652 ;; it should be done with splitters.
7653
7654 (define_expand "and<mode>3"
7655   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
7656         (and:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
7657                   (match_operand:SWIM 2 "<general_szext_operand>" "")))]
7658   ""
7659 {
7660   if (<MODE>mode == DImode
7661       && GET_CODE (operands[2]) == CONST_INT
7662       && INTVAL (operands[2]) == (HOST_WIDE_INT) 0xffffffff
7663       && REG_P (operands[1]))
7664     emit_insn (gen_zero_extendsidi2 (operands[0],
7665                                      gen_lowpart (SImode, operands[1])));
7666   else
7667     ix86_expand_binary_operator (AND, <MODE>mode, operands);
7668   DONE;
7669 })
7670
7671 (define_insn "*anddi_1"
7672   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
7673         (and:DI
7674          (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
7675          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
7676    (clobber (reg:CC FLAGS_REG))]
7677   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
7678 {
7679   switch (get_attr_type (insn))
7680     {
7681     case TYPE_IMOVX:
7682       {
7683         enum machine_mode mode;
7684
7685         gcc_assert (CONST_INT_P (operands[2]));
7686         if (INTVAL (operands[2]) == (HOST_WIDE_INT) 0xffffffff)
7687           mode = SImode;
7688         else if (INTVAL (operands[2]) == 0xffff)
7689           mode = HImode;
7690         else
7691           {
7692             gcc_assert (INTVAL (operands[2]) == 0xff);
7693             mode = QImode;
7694           }
7695
7696         operands[1] = gen_lowpart (mode, operands[1]);
7697         if (mode == SImode)
7698           return "mov{l}\t{%1, %k0|%k0, %1}";
7699         else if (mode == HImode)
7700           return "movz{wl|x}\t{%1, %k0|%k0, %1}";
7701         else
7702           return "movz{bl|x}\t{%1, %k0|%k0, %1}";
7703       }
7704
7705     default:
7706       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7707       if (get_attr_mode (insn) == MODE_SI)
7708         return "and{l}\t{%k2, %k0|%k0, %k2}";
7709       else
7710         return "and{q}\t{%2, %0|%0, %2}";
7711     }
7712 }
7713   [(set_attr "type" "alu,alu,alu,imovx")
7714    (set_attr "length_immediate" "*,*,*,0")
7715    (set (attr "prefix_rex")
7716      (if_then_else
7717        (and (eq_attr "type" "imovx")
7718             (and (match_test "INTVAL (operands[2]) == 0xff")
7719                  (match_operand 1 "ext_QIreg_operand" "")))
7720        (const_string "1")
7721        (const_string "*")))
7722    (set_attr "mode" "SI,DI,DI,SI")])
7723
7724 (define_insn "*andsi_1"
7725   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7726         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7727                 (match_operand:SI 2 "x86_64_general_operand" "re,rm,L")))
7728    (clobber (reg:CC FLAGS_REG))]
7729   "ix86_binary_operator_ok (AND, SImode, operands)"
7730 {
7731   switch (get_attr_type (insn))
7732     {
7733     case TYPE_IMOVX:
7734       {
7735         enum machine_mode mode;
7736
7737         gcc_assert (CONST_INT_P (operands[2]));
7738         if (INTVAL (operands[2]) == 0xffff)
7739           mode = HImode;
7740         else
7741           {
7742             gcc_assert (INTVAL (operands[2]) == 0xff);
7743             mode = QImode;
7744           }
7745
7746         operands[1] = gen_lowpart (mode, operands[1]);
7747         if (mode == HImode)
7748           return "movz{wl|x}\t{%1, %0|%0, %1}";
7749         else
7750           return "movz{bl|x}\t{%1, %0|%0, %1}";
7751       }
7752
7753     default:
7754       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7755       return "and{l}\t{%2, %0|%0, %2}";
7756     }
7757 }
7758   [(set_attr "type" "alu,alu,imovx")
7759    (set (attr "prefix_rex")
7760      (if_then_else
7761        (and (eq_attr "type" "imovx")
7762             (and (match_test "INTVAL (operands[2]) == 0xff")
7763                  (match_operand 1 "ext_QIreg_operand" "")))
7764        (const_string "1")
7765        (const_string "*")))
7766    (set_attr "length_immediate" "*,*,0")
7767    (set_attr "mode" "SI")])
7768
7769 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7770 (define_insn "*andsi_1_zext"
7771   [(set (match_operand:DI 0 "register_operand" "=r")
7772         (zero_extend:DI
7773           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7774                   (match_operand:SI 2 "x86_64_general_operand" "rme"))))
7775    (clobber (reg:CC FLAGS_REG))]
7776   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
7777   "and{l}\t{%2, %k0|%k0, %2}"
7778   [(set_attr "type" "alu")
7779    (set_attr "mode" "SI")])
7780
7781 (define_insn "*andhi_1"
7782   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
7783         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
7784                 (match_operand:HI 2 "general_operand" "rn,rm,L")))
7785    (clobber (reg:CC FLAGS_REG))]
7786   "ix86_binary_operator_ok (AND, HImode, operands)"
7787 {
7788   switch (get_attr_type (insn))
7789     {
7790     case TYPE_IMOVX:
7791       gcc_assert (CONST_INT_P (operands[2]));
7792       gcc_assert (INTVAL (operands[2]) == 0xff);
7793       return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
7794
7795     default:
7796       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7797
7798       return "and{w}\t{%2, %0|%0, %2}";
7799     }
7800 }
7801   [(set_attr "type" "alu,alu,imovx")
7802    (set_attr "length_immediate" "*,*,0")
7803    (set (attr "prefix_rex")
7804      (if_then_else
7805        (and (eq_attr "type" "imovx")
7806             (match_operand 1 "ext_QIreg_operand" ""))
7807        (const_string "1")
7808        (const_string "*")))
7809    (set_attr "mode" "HI,HI,SI")])
7810
7811 ;; %%% Potential partial reg stall on alternative 2.  What to do?
7812 (define_insn "*andqi_1"
7813   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
7814         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7815                 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
7816    (clobber (reg:CC FLAGS_REG))]
7817   "ix86_binary_operator_ok (AND, QImode, operands)"
7818   "@
7819    and{b}\t{%2, %0|%0, %2}
7820    and{b}\t{%2, %0|%0, %2}
7821    and{l}\t{%k2, %k0|%k0, %k2}"
7822   [(set_attr "type" "alu")
7823    (set_attr "mode" "QI,QI,SI")])
7824
7825 (define_insn "*andqi_1_slp"
7826   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7827         (and:QI (match_dup 0)
7828                 (match_operand:QI 1 "general_operand" "qn,qmn")))
7829    (clobber (reg:CC FLAGS_REG))]
7830   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7831    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7832   "and{b}\t{%1, %0|%0, %1}"
7833   [(set_attr "type" "alu1")
7834    (set_attr "mode" "QI")])
7835
7836 (define_split
7837   [(set (match_operand 0 "register_operand" "")
7838         (and (match_dup 0)
7839              (const_int -65536)))
7840    (clobber (reg:CC FLAGS_REG))]
7841   "(TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)
7842     || optimize_function_for_size_p (cfun)"
7843   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7844   "operands[1] = gen_lowpart (HImode, operands[0]);")
7845
7846 (define_split
7847   [(set (match_operand 0 "ext_register_operand" "")
7848         (and (match_dup 0)
7849              (const_int -256)))
7850    (clobber (reg:CC FLAGS_REG))]
7851   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7852    && reload_completed"
7853   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7854   "operands[1] = gen_lowpart (QImode, operands[0]);")
7855
7856 (define_split
7857   [(set (match_operand 0 "ext_register_operand" "")
7858         (and (match_dup 0)
7859              (const_int -65281)))
7860    (clobber (reg:CC FLAGS_REG))]
7861   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7862    && reload_completed"
7863   [(parallel [(set (zero_extract:SI (match_dup 0)
7864                                     (const_int 8)
7865                                     (const_int 8))
7866                    (xor:SI
7867                      (zero_extract:SI (match_dup 0)
7868                                       (const_int 8)
7869                                       (const_int 8))
7870                      (zero_extract:SI (match_dup 0)
7871                                       (const_int 8)
7872                                       (const_int 8))))
7873               (clobber (reg:CC FLAGS_REG))])]
7874   "operands[0] = gen_lowpart (SImode, operands[0]);")
7875
7876 (define_insn "*anddi_2"
7877   [(set (reg FLAGS_REG)
7878         (compare
7879          (and:DI
7880           (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
7881           (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
7882          (const_int 0)))
7883    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
7884         (and:DI (match_dup 1) (match_dup 2)))]
7885   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7886    && ix86_binary_operator_ok (AND, DImode, operands)"
7887   "@
7888    and{l}\t{%k2, %k0|%k0, %k2}
7889    and{q}\t{%2, %0|%0, %2}
7890    and{q}\t{%2, %0|%0, %2}"
7891   [(set_attr "type" "alu")
7892    (set_attr "mode" "SI,DI,DI")])
7893
7894 (define_insn "*andqi_2_maybe_si"
7895   [(set (reg FLAGS_REG)
7896         (compare (and:QI
7897                   (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7898                   (match_operand:QI 2 "general_operand" "qmn,qn,n"))
7899                  (const_int 0)))
7900    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
7901         (and:QI (match_dup 1) (match_dup 2)))]
7902   "ix86_binary_operator_ok (AND, QImode, operands)
7903    && ix86_match_ccmode (insn,
7904                          CONST_INT_P (operands[2])
7905                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
7906 {
7907   if (which_alternative == 2)
7908     {
7909       if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
7910         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
7911       return "and{l}\t{%2, %k0|%k0, %2}";
7912     }
7913   return "and{b}\t{%2, %0|%0, %2}";
7914 }
7915   [(set_attr "type" "alu")
7916    (set_attr "mode" "QI,QI,SI")])
7917
7918 (define_insn "*and<mode>_2"
7919   [(set (reg FLAGS_REG)
7920         (compare (and:SWI124
7921                   (match_operand:SWI124 1 "nonimmediate_operand" "%0,0")
7922                   (match_operand:SWI124 2 "<general_operand>" "<g>,<r><i>"))
7923                  (const_int 0)))
7924    (set (match_operand:SWI124 0 "nonimmediate_operand" "=<r>,<r>m")
7925         (and:SWI124 (match_dup 1) (match_dup 2)))]
7926   "ix86_match_ccmode (insn, CCNOmode)
7927    && ix86_binary_operator_ok (AND, <MODE>mode, operands)"
7928   "and{<imodesuffix>}\t{%2, %0|%0, %2}"
7929   [(set_attr "type" "alu")
7930    (set_attr "mode" "<MODE>")])
7931
7932 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7933 (define_insn "*andsi_2_zext"
7934   [(set (reg FLAGS_REG)
7935         (compare (and:SI
7936                   (match_operand:SI 1 "nonimmediate_operand" "%0")
7937                   (match_operand:SI 2 "x86_64_general_operand" "rme"))
7938                  (const_int 0)))
7939    (set (match_operand:DI 0 "register_operand" "=r")
7940         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
7941   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7942    && ix86_binary_operator_ok (AND, SImode, operands)"
7943   "and{l}\t{%2, %k0|%k0, %2}"
7944   [(set_attr "type" "alu")
7945    (set_attr "mode" "SI")])
7946
7947 (define_insn "*andqi_2_slp"
7948   [(set (reg FLAGS_REG)
7949         (compare (and:QI
7950                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
7951                    (match_operand:QI 1 "nonimmediate_operand" "qmn,qn"))
7952                  (const_int 0)))
7953    (set (strict_low_part (match_dup 0))
7954         (and:QI (match_dup 0) (match_dup 1)))]
7955   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7956    && ix86_match_ccmode (insn, CCNOmode)
7957    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7958   "and{b}\t{%1, %0|%0, %1}"
7959   [(set_attr "type" "alu1")
7960    (set_attr "mode" "QI")])
7961
7962 ;; ??? A bug in recog prevents it from recognizing a const_int as an
7963 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
7964 ;; for a QImode operand, which of course failed.
7965 (define_insn "andqi_ext_0"
7966   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7967                          (const_int 8)
7968                          (const_int 8))
7969         (and:SI
7970           (zero_extract:SI
7971             (match_operand 1 "ext_register_operand" "0")
7972             (const_int 8)
7973             (const_int 8))
7974           (match_operand 2 "const_int_operand" "n")))
7975    (clobber (reg:CC FLAGS_REG))]
7976   ""
7977   "and{b}\t{%2, %h0|%h0, %2}"
7978   [(set_attr "type" "alu")
7979    (set_attr "length_immediate" "1")
7980    (set_attr "modrm" "1")
7981    (set_attr "mode" "QI")])
7982
7983 ;; Generated by peephole translating test to and.  This shows up
7984 ;; often in fp comparisons.
7985 (define_insn "*andqi_ext_0_cc"
7986   [(set (reg FLAGS_REG)
7987         (compare
7988           (and:SI
7989             (zero_extract:SI
7990               (match_operand 1 "ext_register_operand" "0")
7991               (const_int 8)
7992               (const_int 8))
7993             (match_operand 2 "const_int_operand" "n"))
7994           (const_int 0)))
7995    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7996                          (const_int 8)
7997                          (const_int 8))
7998         (and:SI
7999           (zero_extract:SI
8000             (match_dup 1)
8001             (const_int 8)
8002             (const_int 8))
8003           (match_dup 2)))]
8004   "ix86_match_ccmode (insn, CCNOmode)"
8005   "and{b}\t{%2, %h0|%h0, %2}"
8006   [(set_attr "type" "alu")
8007    (set_attr "length_immediate" "1")
8008    (set_attr "modrm" "1")
8009    (set_attr "mode" "QI")])
8010
8011 (define_insn "*andqi_ext_1_rex64"
8012   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8013                          (const_int 8)
8014                          (const_int 8))
8015         (and:SI
8016           (zero_extract:SI
8017             (match_operand 1 "ext_register_operand" "0")
8018             (const_int 8)
8019             (const_int 8))
8020           (zero_extend:SI
8021             (match_operand 2 "ext_register_operand" "Q"))))
8022    (clobber (reg:CC FLAGS_REG))]
8023   "TARGET_64BIT"
8024   "and{b}\t{%2, %h0|%h0, %2}"
8025   [(set_attr "type" "alu")
8026    (set_attr "length_immediate" "0")
8027    (set_attr "mode" "QI")])
8028
8029 (define_insn "*andqi_ext_1"
8030   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8031                          (const_int 8)
8032                          (const_int 8))
8033         (and:SI
8034           (zero_extract:SI
8035             (match_operand 1 "ext_register_operand" "0")
8036             (const_int 8)
8037             (const_int 8))
8038           (zero_extend:SI
8039             (match_operand:QI 2 "general_operand" "Qm"))))
8040    (clobber (reg:CC FLAGS_REG))]
8041   "!TARGET_64BIT"
8042   "and{b}\t{%2, %h0|%h0, %2}"
8043   [(set_attr "type" "alu")
8044    (set_attr "length_immediate" "0")
8045    (set_attr "mode" "QI")])
8046
8047 (define_insn "*andqi_ext_2"
8048   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8049                          (const_int 8)
8050                          (const_int 8))
8051         (and:SI
8052           (zero_extract:SI
8053             (match_operand 1 "ext_register_operand" "%0")
8054             (const_int 8)
8055             (const_int 8))
8056           (zero_extract:SI
8057             (match_operand 2 "ext_register_operand" "Q")
8058             (const_int 8)
8059             (const_int 8))))
8060    (clobber (reg:CC FLAGS_REG))]
8061   ""
8062   "and{b}\t{%h2, %h0|%h0, %h2}"
8063   [(set_attr "type" "alu")
8064    (set_attr "length_immediate" "0")
8065    (set_attr "mode" "QI")])
8066
8067 ;; Convert wide AND instructions with immediate operand to shorter QImode
8068 ;; equivalents when possible.
8069 ;; Don't do the splitting with memory operands, since it introduces risk
8070 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
8071 ;; for size, but that can (should?) be handled by generic code instead.
8072 (define_split
8073   [(set (match_operand 0 "register_operand" "")
8074         (and (match_operand 1 "register_operand" "")
8075              (match_operand 2 "const_int_operand" "")))
8076    (clobber (reg:CC FLAGS_REG))]
8077    "reload_completed
8078     && QI_REG_P (operands[0])
8079     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8080     && !(~INTVAL (operands[2]) & ~(255 << 8))
8081     && GET_MODE (operands[0]) != QImode"
8082   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8083                    (and:SI (zero_extract:SI (match_dup 1)
8084                                             (const_int 8) (const_int 8))
8085                            (match_dup 2)))
8086               (clobber (reg:CC FLAGS_REG))])]
8087 {
8088   operands[0] = gen_lowpart (SImode, operands[0]);
8089   operands[1] = gen_lowpart (SImode, operands[1]);
8090   operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);
8091 })
8092
8093 ;; Since AND can be encoded with sign extended immediate, this is only
8094 ;; profitable when 7th bit is not set.
8095 (define_split
8096   [(set (match_operand 0 "register_operand" "")
8097         (and (match_operand 1 "general_operand" "")
8098              (match_operand 2 "const_int_operand" "")))
8099    (clobber (reg:CC FLAGS_REG))]
8100    "reload_completed
8101     && ANY_QI_REG_P (operands[0])
8102     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8103     && !(~INTVAL (operands[2]) & ~255)
8104     && !(INTVAL (operands[2]) & 128)
8105     && GET_MODE (operands[0]) != QImode"
8106   [(parallel [(set (strict_low_part (match_dup 0))
8107                    (and:QI (match_dup 1)
8108                            (match_dup 2)))
8109               (clobber (reg:CC FLAGS_REG))])]
8110 {
8111   operands[0] = gen_lowpart (QImode, operands[0]);
8112   operands[1] = gen_lowpart (QImode, operands[1]);
8113   operands[2] = gen_lowpart (QImode, operands[2]);
8114 })
8115 \f
8116 ;; Logical inclusive and exclusive OR instructions
8117
8118 ;; %%% This used to optimize known byte-wide and operations to memory.
8119 ;; If this is considered useful, it should be done with splitters.
8120
8121 (define_expand "<code><mode>3"
8122   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8123         (any_or:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
8124                      (match_operand:SWIM 2 "<general_operand>" "")))]
8125   ""
8126   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
8127
8128 (define_insn "*<code><mode>_1"
8129   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=r,rm")
8130         (any_or:SWI248
8131          (match_operand:SWI248 1 "nonimmediate_operand" "%0,0")
8132          (match_operand:SWI248 2 "<general_operand>" "<g>,r<i>")))
8133    (clobber (reg:CC FLAGS_REG))]
8134   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8135   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8136   [(set_attr "type" "alu")
8137    (set_attr "mode" "<MODE>")])
8138
8139 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8140 (define_insn "*<code>qi_1"
8141   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8142         (any_or:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8143                    (match_operand:QI 2 "general_operand" "qmn,qn,rn")))
8144    (clobber (reg:CC FLAGS_REG))]
8145   "ix86_binary_operator_ok (<CODE>, QImode, operands)"
8146   "@
8147    <logic>{b}\t{%2, %0|%0, %2}
8148    <logic>{b}\t{%2, %0|%0, %2}
8149    <logic>{l}\t{%k2, %k0|%k0, %k2}"
8150   [(set_attr "type" "alu")
8151    (set_attr "mode" "QI,QI,SI")])
8152
8153 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8154 (define_insn "*<code>si_1_zext"
8155   [(set (match_operand:DI 0 "register_operand" "=r")
8156         (zero_extend:DI
8157          (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8158                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
8159    (clobber (reg:CC FLAGS_REG))]
8160   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8161   "<logic>{l}\t{%2, %k0|%k0, %2}"
8162   [(set_attr "type" "alu")
8163    (set_attr "mode" "SI")])
8164
8165 (define_insn "*<code>si_1_zext_imm"
8166   [(set (match_operand:DI 0 "register_operand" "=r")
8167         (any_or:DI
8168          (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8169          (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8170    (clobber (reg:CC FLAGS_REG))]
8171   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8172   "<logic>{l}\t{%2, %k0|%k0, %2}"
8173   [(set_attr "type" "alu")
8174    (set_attr "mode" "SI")])
8175
8176 (define_insn "*<code>qi_1_slp"
8177   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8178         (any_or:QI (match_dup 0)
8179                    (match_operand:QI 1 "general_operand" "qmn,qn")))
8180    (clobber (reg:CC FLAGS_REG))]
8181   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8182    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8183   "<logic>{b}\t{%1, %0|%0, %1}"
8184   [(set_attr "type" "alu1")
8185    (set_attr "mode" "QI")])
8186
8187 (define_insn "*<code><mode>_2"
8188   [(set (reg FLAGS_REG)
8189         (compare (any_or:SWI
8190                   (match_operand:SWI 1 "nonimmediate_operand" "%0,0")
8191                   (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>"))
8192                  (const_int 0)))
8193    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m")
8194         (any_or:SWI (match_dup 1) (match_dup 2)))]
8195   "ix86_match_ccmode (insn, CCNOmode)
8196    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8197   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8198   [(set_attr "type" "alu")
8199    (set_attr "mode" "<MODE>")])
8200
8201 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8202 ;; ??? Special case for immediate operand is missing - it is tricky.
8203 (define_insn "*<code>si_2_zext"
8204   [(set (reg FLAGS_REG)
8205         (compare (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8206                             (match_operand:SI 2 "x86_64_general_operand" "rme"))
8207                  (const_int 0)))
8208    (set (match_operand:DI 0 "register_operand" "=r")
8209         (zero_extend:DI (any_or:SI (match_dup 1) (match_dup 2))))]
8210   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8211    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8212   "<logic>{l}\t{%2, %k0|%k0, %2}"
8213   [(set_attr "type" "alu")
8214    (set_attr "mode" "SI")])
8215
8216 (define_insn "*<code>si_2_zext_imm"
8217   [(set (reg FLAGS_REG)
8218         (compare (any_or:SI
8219                   (match_operand:SI 1 "nonimmediate_operand" "%0")
8220                   (match_operand:SI 2 "x86_64_zext_immediate_operand" "Z"))
8221                  (const_int 0)))
8222    (set (match_operand:DI 0 "register_operand" "=r")
8223         (any_or:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8224   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8225    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8226   "<logic>{l}\t{%2, %k0|%k0, %2}"
8227   [(set_attr "type" "alu")
8228    (set_attr "mode" "SI")])
8229
8230 (define_insn "*<code>qi_2_slp"
8231   [(set (reg FLAGS_REG)
8232         (compare (any_or:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8233                             (match_operand:QI 1 "general_operand" "qmn,qn"))
8234                  (const_int 0)))
8235    (set (strict_low_part (match_dup 0))
8236         (any_or:QI (match_dup 0) (match_dup 1)))]
8237   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8238    && ix86_match_ccmode (insn, CCNOmode)
8239    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8240   "<logic>{b}\t{%1, %0|%0, %1}"
8241   [(set_attr "type" "alu1")
8242    (set_attr "mode" "QI")])
8243
8244 (define_insn "*<code><mode>_3"
8245   [(set (reg FLAGS_REG)
8246         (compare (any_or:SWI
8247                   (match_operand:SWI 1 "nonimmediate_operand" "%0")
8248                   (match_operand:SWI 2 "<general_operand>" "<g>"))
8249                  (const_int 0)))
8250    (clobber (match_scratch:SWI 0 "=<r>"))]
8251   "ix86_match_ccmode (insn, CCNOmode)
8252    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8253   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8254   [(set_attr "type" "alu")
8255    (set_attr "mode" "<MODE>")])
8256
8257 (define_insn "*<code>qi_ext_0"
8258   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8259                          (const_int 8)
8260                          (const_int 8))
8261         (any_or:SI
8262           (zero_extract:SI
8263             (match_operand 1 "ext_register_operand" "0")
8264             (const_int 8)
8265             (const_int 8))
8266           (match_operand 2 "const_int_operand" "n")))
8267    (clobber (reg:CC FLAGS_REG))]
8268   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8269   "<logic>{b}\t{%2, %h0|%h0, %2}"
8270   [(set_attr "type" "alu")
8271    (set_attr "length_immediate" "1")
8272    (set_attr "modrm" "1")
8273    (set_attr "mode" "QI")])
8274
8275 (define_insn "*<code>qi_ext_1_rex64"
8276   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8277                          (const_int 8)
8278                          (const_int 8))
8279         (any_or:SI
8280           (zero_extract:SI
8281             (match_operand 1 "ext_register_operand" "0")
8282             (const_int 8)
8283             (const_int 8))
8284           (zero_extend:SI
8285             (match_operand 2 "ext_register_operand" "Q"))))
8286    (clobber (reg:CC FLAGS_REG))]
8287   "TARGET_64BIT
8288    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8289   "<logic>{b}\t{%2, %h0|%h0, %2}"
8290   [(set_attr "type" "alu")
8291    (set_attr "length_immediate" "0")
8292    (set_attr "mode" "QI")])
8293
8294 (define_insn "*<code>qi_ext_1"
8295   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8296                          (const_int 8)
8297                          (const_int 8))
8298         (any_or:SI
8299           (zero_extract:SI
8300             (match_operand 1 "ext_register_operand" "0")
8301             (const_int 8)
8302             (const_int 8))
8303           (zero_extend:SI
8304             (match_operand:QI 2 "general_operand" "Qm"))))
8305    (clobber (reg:CC FLAGS_REG))]
8306   "!TARGET_64BIT
8307    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8308   "<logic>{b}\t{%2, %h0|%h0, %2}"
8309   [(set_attr "type" "alu")
8310    (set_attr "length_immediate" "0")
8311    (set_attr "mode" "QI")])
8312
8313 (define_insn "*<code>qi_ext_2"
8314   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8315                          (const_int 8)
8316                          (const_int 8))
8317         (any_or:SI
8318           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8319                            (const_int 8)
8320                            (const_int 8))
8321           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8322                            (const_int 8)
8323                            (const_int 8))))
8324    (clobber (reg:CC FLAGS_REG))]
8325   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8326   "<logic>{b}\t{%h2, %h0|%h0, %h2}"
8327   [(set_attr "type" "alu")
8328    (set_attr "length_immediate" "0")
8329    (set_attr "mode" "QI")])
8330
8331 (define_split
8332   [(set (match_operand 0 "register_operand" "")
8333         (any_or (match_operand 1 "register_operand" "")
8334                 (match_operand 2 "const_int_operand" "")))
8335    (clobber (reg:CC FLAGS_REG))]
8336    "reload_completed
8337     && QI_REG_P (operands[0])
8338     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8339     && !(INTVAL (operands[2]) & ~(255 << 8))
8340     && GET_MODE (operands[0]) != QImode"
8341   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8342                    (any_or:SI (zero_extract:SI (match_dup 1)
8343                                                (const_int 8) (const_int 8))
8344                               (match_dup 2)))
8345               (clobber (reg:CC FLAGS_REG))])]
8346 {
8347   operands[0] = gen_lowpart (SImode, operands[0]);
8348   operands[1] = gen_lowpart (SImode, operands[1]);
8349   operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);
8350 })
8351
8352 ;; Since OR can be encoded with sign extended immediate, this is only
8353 ;; profitable when 7th bit is set.
8354 (define_split
8355   [(set (match_operand 0 "register_operand" "")
8356         (any_or (match_operand 1 "general_operand" "")
8357                 (match_operand 2 "const_int_operand" "")))
8358    (clobber (reg:CC FLAGS_REG))]
8359    "reload_completed
8360     && ANY_QI_REG_P (operands[0])
8361     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8362     && !(INTVAL (operands[2]) & ~255)
8363     && (INTVAL (operands[2]) & 128)
8364     && GET_MODE (operands[0]) != QImode"
8365   [(parallel [(set (strict_low_part (match_dup 0))
8366                    (any_or:QI (match_dup 1)
8367                               (match_dup 2)))
8368               (clobber (reg:CC FLAGS_REG))])]
8369 {
8370   operands[0] = gen_lowpart (QImode, operands[0]);
8371   operands[1] = gen_lowpart (QImode, operands[1]);
8372   operands[2] = gen_lowpart (QImode, operands[2]);
8373 })
8374
8375 (define_expand "xorqi_cc_ext_1"
8376   [(parallel [
8377      (set (reg:CCNO FLAGS_REG)
8378           (compare:CCNO
8379             (xor:SI
8380               (zero_extract:SI
8381                 (match_operand 1 "ext_register_operand" "")
8382                 (const_int 8)
8383                 (const_int 8))
8384               (match_operand:QI 2 "general_operand" ""))
8385             (const_int 0)))
8386      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
8387                            (const_int 8)
8388                            (const_int 8))
8389           (xor:SI
8390             (zero_extract:SI
8391              (match_dup 1)
8392              (const_int 8)
8393              (const_int 8))
8394             (match_dup 2)))])])
8395
8396 (define_insn "*xorqi_cc_ext_1_rex64"
8397   [(set (reg FLAGS_REG)
8398         (compare
8399           (xor:SI
8400             (zero_extract:SI
8401               (match_operand 1 "ext_register_operand" "0")
8402               (const_int 8)
8403               (const_int 8))
8404             (match_operand:QI 2 "nonmemory_operand" "Qn"))
8405           (const_int 0)))
8406    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8407                          (const_int 8)
8408                          (const_int 8))
8409         (xor:SI
8410           (zero_extract:SI
8411            (match_dup 1)
8412            (const_int 8)
8413            (const_int 8))
8414           (match_dup 2)))]
8415   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8416   "xor{b}\t{%2, %h0|%h0, %2}"
8417   [(set_attr "type" "alu")
8418    (set_attr "modrm" "1")
8419    (set_attr "mode" "QI")])
8420
8421 (define_insn "*xorqi_cc_ext_1"
8422   [(set (reg FLAGS_REG)
8423         (compare
8424           (xor:SI
8425             (zero_extract:SI
8426               (match_operand 1 "ext_register_operand" "0")
8427               (const_int 8)
8428               (const_int 8))
8429             (match_operand:QI 2 "general_operand" "qmn"))
8430           (const_int 0)))
8431    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
8432                          (const_int 8)
8433                          (const_int 8))
8434         (xor:SI
8435           (zero_extract:SI
8436            (match_dup 1)
8437            (const_int 8)
8438            (const_int 8))
8439           (match_dup 2)))]
8440   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8441   "xor{b}\t{%2, %h0|%h0, %2}"
8442   [(set_attr "type" "alu")
8443    (set_attr "modrm" "1")
8444    (set_attr "mode" "QI")])
8445 \f
8446 ;; Negation instructions
8447
8448 (define_expand "neg<mode>2"
8449   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
8450         (neg:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")))]
8451   ""
8452   "ix86_expand_unary_operator (NEG, <MODE>mode, operands); DONE;")
8453
8454 (define_insn_and_split "*neg<dwi>2_doubleword"
8455   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=ro")
8456         (neg:<DWI> (match_operand:<DWI> 1 "nonimmediate_operand" "0")))
8457    (clobber (reg:CC FLAGS_REG))]
8458   "ix86_unary_operator_ok (NEG, <DWI>mode, operands)"
8459   "#"
8460   "reload_completed"
8461   [(parallel
8462     [(set (reg:CCZ FLAGS_REG)
8463           (compare:CCZ (neg:DWIH (match_dup 1)) (const_int 0)))
8464      (set (match_dup 0) (neg:DWIH (match_dup 1)))])
8465    (parallel
8466     [(set (match_dup 2)
8467           (plus:DWIH (match_dup 3)
8468                      (plus:DWIH (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
8469                                 (const_int 0))))
8470      (clobber (reg:CC FLAGS_REG))])
8471    (parallel
8472     [(set (match_dup 2)
8473           (neg:DWIH (match_dup 2)))
8474      (clobber (reg:CC FLAGS_REG))])]
8475   "split_double_mode (<DWI>mode, &operands[0], 2, &operands[0], &operands[2]);")
8476
8477 (define_insn "*neg<mode>2_1"
8478   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8479         (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")))
8480    (clobber (reg:CC FLAGS_REG))]
8481   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8482   "neg{<imodesuffix>}\t%0"
8483   [(set_attr "type" "negnot")
8484    (set_attr "mode" "<MODE>")])
8485
8486 ;; Combine is quite creative about this pattern.
8487 (define_insn "*negsi2_1_zext"
8488   [(set (match_operand:DI 0 "register_operand" "=r")
8489         (lshiftrt:DI
8490           (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
8491                              (const_int 32)))
8492         (const_int 32)))
8493    (clobber (reg:CC FLAGS_REG))]
8494   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8495   "neg{l}\t%k0"
8496   [(set_attr "type" "negnot")
8497    (set_attr "mode" "SI")])
8498
8499 ;; The problem with neg is that it does not perform (compare x 0),
8500 ;; it really performs (compare 0 x), which leaves us with the zero
8501 ;; flag being the only useful item.
8502
8503 (define_insn "*neg<mode>2_cmpz"
8504   [(set (reg:CCZ FLAGS_REG)
8505         (compare:CCZ
8506           (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8507                    (const_int 0)))
8508    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8509         (neg:SWI (match_dup 1)))]
8510   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8511   "neg{<imodesuffix>}\t%0"
8512   [(set_attr "type" "negnot")
8513    (set_attr "mode" "<MODE>")])
8514
8515 (define_insn "*negsi2_cmpz_zext"
8516   [(set (reg:CCZ FLAGS_REG)
8517         (compare:CCZ
8518           (lshiftrt:DI
8519             (neg:DI (ashift:DI
8520                       (match_operand:DI 1 "register_operand" "0")
8521                       (const_int 32)))
8522             (const_int 32))
8523           (const_int 0)))
8524    (set (match_operand:DI 0 "register_operand" "=r")
8525         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
8526                                         (const_int 32)))
8527                      (const_int 32)))]
8528   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8529   "neg{l}\t%k0"
8530   [(set_attr "type" "negnot")
8531    (set_attr "mode" "SI")])
8532
8533 ;; Changing of sign for FP values is doable using integer unit too.
8534
8535 (define_expand "<code><mode>2"
8536   [(set (match_operand:X87MODEF 0 "register_operand" "")
8537         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
8538   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8539   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
8540
8541 (define_insn "*absneg<mode>2_mixed"
8542   [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
8543         (match_operator:MODEF 3 "absneg_operator"
8544           [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
8545    (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
8546    (clobber (reg:CC FLAGS_REG))]
8547   "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
8548   "#")
8549
8550 (define_insn "*absneg<mode>2_sse"
8551   [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
8552         (match_operator:MODEF 3 "absneg_operator"
8553           [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
8554    (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
8555    (clobber (reg:CC FLAGS_REG))]
8556   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
8557   "#")
8558
8559 (define_insn "*absneg<mode>2_i387"
8560   [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
8561         (match_operator:X87MODEF 3 "absneg_operator"
8562           [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
8563    (use (match_operand 2 "" ""))
8564    (clobber (reg:CC FLAGS_REG))]
8565   "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8566   "#")
8567
8568 (define_expand "<code>tf2"
8569   [(set (match_operand:TF 0 "register_operand" "")
8570         (absneg:TF (match_operand:TF 1 "register_operand" "")))]
8571   "TARGET_SSE2"
8572   "ix86_expand_fp_absneg_operator (<CODE>, TFmode, operands); DONE;")
8573
8574 (define_insn "*absnegtf2_sse"
8575   [(set (match_operand:TF 0 "register_operand" "=x,x")
8576         (match_operator:TF 3 "absneg_operator"
8577           [(match_operand:TF 1 "register_operand" "0,x")]))
8578    (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
8579    (clobber (reg:CC FLAGS_REG))]
8580   "TARGET_SSE2"
8581   "#")
8582
8583 ;; Splitters for fp abs and neg.
8584
8585 (define_split
8586   [(set (match_operand 0 "fp_register_operand" "")
8587         (match_operator 1 "absneg_operator" [(match_dup 0)]))
8588    (use (match_operand 2 "" ""))
8589    (clobber (reg:CC FLAGS_REG))]
8590   "reload_completed"
8591   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
8592
8593 (define_split
8594   [(set (match_operand 0 "register_operand" "")
8595         (match_operator 3 "absneg_operator"
8596           [(match_operand 1 "register_operand" "")]))
8597    (use (match_operand 2 "nonimmediate_operand" ""))
8598    (clobber (reg:CC FLAGS_REG))]
8599   "reload_completed && SSE_REG_P (operands[0])"
8600   [(set (match_dup 0) (match_dup 3))]
8601 {
8602   enum machine_mode mode = GET_MODE (operands[0]);
8603   enum machine_mode vmode = GET_MODE (operands[2]);
8604   rtx tmp;
8605
8606   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
8607   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
8608   if (operands_match_p (operands[0], operands[2]))
8609     {
8610       tmp = operands[1];
8611       operands[1] = operands[2];
8612       operands[2] = tmp;
8613     }
8614   if (GET_CODE (operands[3]) == ABS)
8615     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
8616   else
8617     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
8618   operands[3] = tmp;
8619 })
8620
8621 (define_split
8622   [(set (match_operand:SF 0 "register_operand" "")
8623         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
8624    (use (match_operand:V4SF 2 "" ""))
8625    (clobber (reg:CC FLAGS_REG))]
8626   "reload_completed"
8627   [(parallel [(set (match_dup 0) (match_dup 1))
8628               (clobber (reg:CC FLAGS_REG))])]
8629 {
8630   rtx tmp;
8631   operands[0] = gen_lowpart (SImode, operands[0]);
8632   if (GET_CODE (operands[1]) == ABS)
8633     {
8634       tmp = gen_int_mode (0x7fffffff, SImode);
8635       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8636     }
8637   else
8638     {
8639       tmp = gen_int_mode (0x80000000, SImode);
8640       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8641     }
8642   operands[1] = tmp;
8643 })
8644
8645 (define_split
8646   [(set (match_operand:DF 0 "register_operand" "")
8647         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
8648    (use (match_operand 2 "" ""))
8649    (clobber (reg:CC FLAGS_REG))]
8650   "reload_completed"
8651   [(parallel [(set (match_dup 0) (match_dup 1))
8652               (clobber (reg:CC FLAGS_REG))])]
8653 {
8654   rtx tmp;
8655   if (TARGET_64BIT)
8656     {
8657       tmp = gen_lowpart (DImode, operands[0]);
8658       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
8659       operands[0] = tmp;
8660
8661       if (GET_CODE (operands[1]) == ABS)
8662         tmp = const0_rtx;
8663       else
8664         tmp = gen_rtx_NOT (DImode, tmp);
8665     }
8666   else
8667     {
8668       operands[0] = gen_highpart (SImode, operands[0]);
8669       if (GET_CODE (operands[1]) == ABS)
8670         {
8671           tmp = gen_int_mode (0x7fffffff, SImode);
8672           tmp = gen_rtx_AND (SImode, operands[0], tmp);
8673         }
8674       else
8675         {
8676           tmp = gen_int_mode (0x80000000, SImode);
8677           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8678         }
8679     }
8680   operands[1] = tmp;
8681 })
8682
8683 (define_split
8684   [(set (match_operand:XF 0 "register_operand" "")
8685         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
8686    (use (match_operand 2 "" ""))
8687    (clobber (reg:CC FLAGS_REG))]
8688   "reload_completed"
8689   [(parallel [(set (match_dup 0) (match_dup 1))
8690               (clobber (reg:CC FLAGS_REG))])]
8691 {
8692   rtx tmp;
8693   operands[0] = gen_rtx_REG (SImode,
8694                              true_regnum (operands[0])
8695                              + (TARGET_64BIT ? 1 : 2));
8696   if (GET_CODE (operands[1]) == ABS)
8697     {
8698       tmp = GEN_INT (0x7fff);
8699       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8700     }
8701   else
8702     {
8703       tmp = GEN_INT (0x8000);
8704       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8705     }
8706   operands[1] = tmp;
8707 })
8708
8709 ;; Conditionalize these after reload. If they match before reload, we
8710 ;; lose the clobber and ability to use integer instructions.
8711
8712 (define_insn "*<code><mode>2_1"
8713   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
8714         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
8715   "TARGET_80387
8716    && (reload_completed
8717        || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
8718   "f<absneg_mnemonic>"
8719   [(set_attr "type" "fsgn")
8720    (set_attr "mode" "<MODE>")])
8721
8722 (define_insn "*<code>extendsfdf2"
8723   [(set (match_operand:DF 0 "register_operand" "=f")
8724         (absneg:DF (float_extend:DF
8725                      (match_operand:SF 1 "register_operand" "0"))))]
8726   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
8727   "f<absneg_mnemonic>"
8728   [(set_attr "type" "fsgn")
8729    (set_attr "mode" "DF")])
8730
8731 (define_insn "*<code>extendsfxf2"
8732   [(set (match_operand:XF 0 "register_operand" "=f")
8733         (absneg:XF (float_extend:XF
8734                      (match_operand:SF 1 "register_operand" "0"))))]
8735   "TARGET_80387"
8736   "f<absneg_mnemonic>"
8737   [(set_attr "type" "fsgn")
8738    (set_attr "mode" "XF")])
8739
8740 (define_insn "*<code>extenddfxf2"
8741   [(set (match_operand:XF 0 "register_operand" "=f")
8742         (absneg:XF (float_extend:XF
8743                      (match_operand:DF 1 "register_operand" "0"))))]
8744   "TARGET_80387"
8745   "f<absneg_mnemonic>"
8746   [(set_attr "type" "fsgn")
8747    (set_attr "mode" "XF")])
8748
8749 ;; Copysign instructions
8750
8751 (define_mode_iterator CSGNMODE [SF DF TF])
8752 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
8753
8754 (define_expand "copysign<mode>3"
8755   [(match_operand:CSGNMODE 0 "register_operand" "")
8756    (match_operand:CSGNMODE 1 "nonmemory_operand" "")
8757    (match_operand:CSGNMODE 2 "register_operand" "")]
8758   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8759    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8760   "ix86_expand_copysign (operands); DONE;")
8761
8762 (define_insn_and_split "copysign<mode>3_const"
8763   [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
8764         (unspec:CSGNMODE
8765           [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
8766            (match_operand:CSGNMODE 2 "register_operand" "0")
8767            (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
8768           UNSPEC_COPYSIGN))]
8769   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8770    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8771   "#"
8772   "&& reload_completed"
8773   [(const_int 0)]
8774   "ix86_split_copysign_const (operands); DONE;")
8775
8776 (define_insn "copysign<mode>3_var"
8777   [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
8778         (unspec:CSGNMODE
8779           [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
8780            (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
8781            (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
8782            (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
8783           UNSPEC_COPYSIGN))
8784    (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
8785   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8786    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8787   "#")
8788
8789 (define_split
8790   [(set (match_operand:CSGNMODE 0 "register_operand" "")
8791         (unspec:CSGNMODE
8792           [(match_operand:CSGNMODE 2 "register_operand" "")
8793            (match_operand:CSGNMODE 3 "register_operand" "")
8794            (match_operand:<CSGNVMODE> 4 "" "")
8795            (match_operand:<CSGNVMODE> 5 "" "")]
8796           UNSPEC_COPYSIGN))
8797    (clobber (match_scratch:<CSGNVMODE> 1 ""))]
8798   "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8799     || (TARGET_SSE2 && (<MODE>mode == TFmode)))
8800    && reload_completed"
8801   [(const_int 0)]
8802   "ix86_split_copysign_var (operands); DONE;")
8803 \f
8804 ;; One complement instructions
8805
8806 (define_expand "one_cmpl<mode>2"
8807   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8808         (not:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")))]
8809   ""
8810   "ix86_expand_unary_operator (NOT, <MODE>mode, operands); DONE;")
8811
8812 (define_insn "*one_cmpl<mode>2_1"
8813   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=rm")
8814         (not:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "0")))]
8815   "ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8816   "not{<imodesuffix>}\t%0"
8817   [(set_attr "type" "negnot")
8818    (set_attr "mode" "<MODE>")])
8819
8820 ;; %%% Potential partial reg stall on alternative 1.  What to do?
8821 (define_insn "*one_cmplqi2_1"
8822   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
8823         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
8824   "ix86_unary_operator_ok (NOT, QImode, operands)"
8825   "@
8826    not{b}\t%0
8827    not{l}\t%k0"
8828   [(set_attr "type" "negnot")
8829    (set_attr "mode" "QI,SI")])
8830
8831 ;; ??? Currently never generated - xor is used instead.
8832 (define_insn "*one_cmplsi2_1_zext"
8833   [(set (match_operand:DI 0 "register_operand" "=r")
8834         (zero_extend:DI
8835           (not:SI (match_operand:SI 1 "register_operand" "0"))))]
8836   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
8837   "not{l}\t%k0"
8838   [(set_attr "type" "negnot")
8839    (set_attr "mode" "SI")])
8840
8841 (define_insn "*one_cmpl<mode>2_2"
8842   [(set (reg FLAGS_REG)
8843         (compare (not:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8844                  (const_int 0)))
8845    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8846         (not:SWI (match_dup 1)))]
8847   "ix86_match_ccmode (insn, CCNOmode)
8848    && ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8849   "#"
8850   [(set_attr "type" "alu1")
8851    (set_attr "mode" "<MODE>")])
8852
8853 (define_split
8854   [(set (match_operand 0 "flags_reg_operand" "")
8855         (match_operator 2 "compare_operator"
8856           [(not:SWI (match_operand:SWI 3 "nonimmediate_operand" ""))
8857            (const_int 0)]))
8858    (set (match_operand:SWI 1 "nonimmediate_operand" "")
8859         (not:SWI (match_dup 3)))]
8860   "ix86_match_ccmode (insn, CCNOmode)"
8861   [(parallel [(set (match_dup 0)
8862                    (match_op_dup 2 [(xor:SWI (match_dup 3) (const_int -1))
8863                                     (const_int 0)]))
8864               (set (match_dup 1)
8865                    (xor:SWI (match_dup 3) (const_int -1)))])])
8866
8867 ;; ??? Currently never generated - xor is used instead.
8868 (define_insn "*one_cmplsi2_2_zext"
8869   [(set (reg FLAGS_REG)
8870         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
8871                  (const_int 0)))
8872    (set (match_operand:DI 0 "register_operand" "=r")
8873         (zero_extend:DI (not:SI (match_dup 1))))]
8874   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8875    && ix86_unary_operator_ok (NOT, SImode, operands)"
8876   "#"
8877   [(set_attr "type" "alu1")
8878    (set_attr "mode" "SI")])
8879
8880 (define_split
8881   [(set (match_operand 0 "flags_reg_operand" "")
8882         (match_operator 2 "compare_operator"
8883           [(not:SI (match_operand:SI 3 "register_operand" ""))
8884            (const_int 0)]))
8885    (set (match_operand:DI 1 "register_operand" "")
8886         (zero_extend:DI (not:SI (match_dup 3))))]
8887   "ix86_match_ccmode (insn, CCNOmode)"
8888   [(parallel [(set (match_dup 0)
8889                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
8890                                     (const_int 0)]))
8891               (set (match_dup 1)
8892                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])])
8893 \f
8894 ;; Shift instructions
8895
8896 ;; DImode shifts are implemented using the i386 "shift double" opcode,
8897 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
8898 ;; is variable, then the count is in %cl and the "imm" operand is dropped
8899 ;; from the assembler input.
8900 ;;
8901 ;; This instruction shifts the target reg/mem as usual, but instead of
8902 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
8903 ;; is a left shift double, bits are taken from the high order bits of
8904 ;; reg, else if the insn is a shift right double, bits are taken from the
8905 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
8906 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
8907 ;;
8908 ;; Since sh[lr]d does not change the `reg' operand, that is done
8909 ;; separately, making all shifts emit pairs of shift double and normal
8910 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
8911 ;; support a 63 bit shift, each shift where the count is in a reg expands
8912 ;; to a pair of shifts, a branch, a shift by 32 and a label.
8913 ;;
8914 ;; If the shift count is a constant, we need never emit more than one
8915 ;; shift pair, instead using moves and sign extension for counts greater
8916 ;; than 31.
8917
8918 (define_expand "ashl<mode>3"
8919   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
8920         (ashift:SDWIM (match_operand:SDWIM 1 "<ashl_input_operand>" "")
8921                       (match_operand:QI 2 "nonmemory_operand" "")))]
8922   ""
8923   "ix86_expand_binary_operator (ASHIFT, <MODE>mode, operands); DONE;")
8924
8925 (define_insn "*ashl<mode>3_doubleword"
8926   [(set (match_operand:DWI 0 "register_operand" "=&r,r")
8927         (ashift:DWI (match_operand:DWI 1 "reg_or_pm1_operand" "n,0")
8928                     (match_operand:QI 2 "nonmemory_operand" "<S>c,<S>c")))
8929    (clobber (reg:CC FLAGS_REG))]
8930   ""
8931   "#"
8932   [(set_attr "type" "multi")])
8933
8934 (define_split
8935   [(set (match_operand:DWI 0 "register_operand" "")
8936         (ashift:DWI (match_operand:DWI 1 "nonmemory_operand" "")
8937                     (match_operand:QI 2 "nonmemory_operand" "")))
8938    (clobber (reg:CC FLAGS_REG))]
8939   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
8940   [(const_int 0)]
8941   "ix86_split_ashl (operands, NULL_RTX, <MODE>mode); DONE;")
8942
8943 ;; By default we don't ask for a scratch register, because when DWImode
8944 ;; values are manipulated, registers are already at a premium.  But if
8945 ;; we have one handy, we won't turn it away.
8946
8947 (define_peephole2
8948   [(match_scratch:DWIH 3 "r")
8949    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
8950                    (ashift:<DWI>
8951                      (match_operand:<DWI> 1 "nonmemory_operand" "")
8952                      (match_operand:QI 2 "nonmemory_operand" "")))
8953               (clobber (reg:CC FLAGS_REG))])
8954    (match_dup 3)]
8955   "TARGET_CMOVE"
8956   [(const_int 0)]
8957   "ix86_split_ashl (operands, operands[3], <DWI>mode); DONE;")
8958
8959 (define_insn "x86_64_shld"
8960   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
8961         (ior:DI (ashift:DI (match_dup 0)
8962                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
8963                 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
8964                   (minus:QI (const_int 64) (match_dup 2)))))
8965    (clobber (reg:CC FLAGS_REG))]
8966   "TARGET_64BIT"
8967   "shld{q}\t{%s2%1, %0|%0, %1, %2}"
8968   [(set_attr "type" "ishift")
8969    (set_attr "prefix_0f" "1")
8970    (set_attr "mode" "DI")
8971    (set_attr "athlon_decode" "vector")
8972    (set_attr "amdfam10_decode" "vector")
8973    (set_attr "bdver1_decode" "vector")])
8974
8975 (define_insn "x86_shld"
8976   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
8977         (ior:SI (ashift:SI (match_dup 0)
8978                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
8979                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
8980                   (minus:QI (const_int 32) (match_dup 2)))))
8981    (clobber (reg:CC FLAGS_REG))]
8982   ""
8983   "shld{l}\t{%s2%1, %0|%0, %1, %2}"
8984   [(set_attr "type" "ishift")
8985    (set_attr "prefix_0f" "1")
8986    (set_attr "mode" "SI")
8987    (set_attr "pent_pair" "np")
8988    (set_attr "athlon_decode" "vector")
8989    (set_attr "amdfam10_decode" "vector")
8990    (set_attr "bdver1_decode" "vector")])
8991
8992 (define_expand "x86_shift<mode>_adj_1"
8993   [(set (reg:CCZ FLAGS_REG)
8994         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
8995                              (match_dup 4))
8996                      (const_int 0)))
8997    (set (match_operand:SWI48 0 "register_operand" "")
8998         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
8999                             (match_operand:SWI48 1 "register_operand" "")
9000                             (match_dup 0)))
9001    (set (match_dup 1)
9002         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
9003                             (match_operand:SWI48 3 "register_operand" "")
9004                             (match_dup 1)))]
9005   "TARGET_CMOVE"
9006   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
9007
9008 (define_expand "x86_shift<mode>_adj_2"
9009   [(use (match_operand:SWI48 0 "register_operand" ""))
9010    (use (match_operand:SWI48 1 "register_operand" ""))
9011    (use (match_operand:QI 2 "register_operand" ""))]
9012   ""
9013 {
9014   rtx label = gen_label_rtx ();
9015   rtx tmp;
9016
9017   emit_insn (gen_testqi_ccz_1 (operands[2],
9018                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9019
9020   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9021   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9022   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9023                               gen_rtx_LABEL_REF (VOIDmode, label),
9024                               pc_rtx);
9025   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9026   JUMP_LABEL (tmp) = label;
9027
9028   emit_move_insn (operands[0], operands[1]);
9029   ix86_expand_clear (operands[1]);
9030
9031   emit_label (label);
9032   LABEL_NUSES (label) = 1;
9033
9034   DONE;
9035 })
9036
9037 ;; Avoid useless masking of count operand.
9038 (define_insn_and_split "*ashl<mode>3_mask"
9039   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9040         (ashift:SWI48
9041           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9042           (subreg:QI
9043             (and:SI
9044               (match_operand:SI 2 "nonimmediate_operand" "c")
9045               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9046    (clobber (reg:CC FLAGS_REG))]
9047   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)
9048    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9049       == GET_MODE_BITSIZE (<MODE>mode)-1"
9050   "#"
9051   "&& 1"
9052   [(parallel [(set (match_dup 0)
9053                    (ashift:SWI48 (match_dup 1) (match_dup 2)))
9054               (clobber (reg:CC FLAGS_REG))])]
9055 {
9056   if (can_create_pseudo_p ())
9057     operands [2] = force_reg (SImode, operands[2]);
9058
9059   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9060 }
9061   [(set_attr "type" "ishift")
9062    (set_attr "mode" "<MODE>")])
9063
9064 (define_insn "*bmi2_ashl<mode>3_1"
9065   [(set (match_operand:SWI48 0 "register_operand" "=r")
9066         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9067                       (match_operand:SWI48 2 "register_operand" "r")))]
9068   "TARGET_BMI2"
9069   "shlx\t{%2, %1, %0|%0, %1, %2}"
9070   [(set_attr "type" "ishiftx")
9071    (set_attr "mode" "<MODE>")])
9072
9073 (define_insn "*ashl<mode>3_1"
9074   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r,r")
9075         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,l,rm")
9076                       (match_operand:QI 2 "nonmemory_operand" "c<S>,M,r")))
9077    (clobber (reg:CC FLAGS_REG))]
9078   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9079 {
9080   switch (get_attr_type (insn))
9081     {
9082     case TYPE_LEA:
9083     case TYPE_ISHIFTX:
9084       return "#";
9085
9086     case TYPE_ALU:
9087       gcc_assert (operands[2] == const1_rtx);
9088       gcc_assert (rtx_equal_p (operands[0], operands[1]));
9089       return "add{<imodesuffix>}\t%0, %0";
9090
9091     default:
9092       if (operands[2] == const1_rtx
9093           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9094         return "sal{<imodesuffix>}\t%0";
9095       else
9096         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9097     }
9098 }
9099   [(set_attr "isa" "*,*,bmi2")
9100    (set (attr "type")
9101      (cond [(eq_attr "alternative" "1")
9102               (const_string "lea")
9103             (eq_attr "alternative" "2")
9104               (const_string "ishiftx")
9105             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9106                       (match_operand 0 "register_operand" ""))
9107                  (match_operand 2 "const1_operand" ""))
9108               (const_string "alu")
9109            ]
9110            (const_string "ishift")))
9111    (set (attr "length_immediate")
9112      (if_then_else
9113        (ior (eq_attr "type" "alu")
9114             (and (eq_attr "type" "ishift")
9115                  (and (match_operand 2 "const1_operand" "")
9116                       (ior (match_test "TARGET_SHIFT1")
9117                            (match_test "optimize_function_for_size_p (cfun)")))))
9118        (const_string "0")
9119        (const_string "*")))
9120    (set_attr "mode" "<MODE>")])
9121
9122 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9123 (define_split
9124   [(set (match_operand:SWI48 0 "register_operand" "")
9125         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9126                       (match_operand:QI 2 "register_operand" "")))
9127    (clobber (reg:CC FLAGS_REG))]
9128   "TARGET_BMI2 && reload_completed"
9129   [(set (match_dup 0)
9130         (ashift:SWI48 (match_dup 1) (match_dup 2)))]
9131   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9132
9133 (define_insn "*bmi2_ashlsi3_1_zext"
9134   [(set (match_operand:DI 0 "register_operand" "=r")
9135         (zero_extend:DI
9136           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9137                      (match_operand:SI 2 "register_operand" "r"))))]
9138   "TARGET_64BIT && TARGET_BMI2"
9139   "shlx\t{%2, %1, %k0|%k0, %1, %2}"
9140   [(set_attr "type" "ishiftx")
9141    (set_attr "mode" "SI")])
9142
9143 (define_insn "*ashlsi3_1_zext"
9144   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
9145         (zero_extend:DI
9146           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l,rm")
9147                      (match_operand:QI 2 "nonmemory_operand" "cI,M,r"))))
9148    (clobber (reg:CC FLAGS_REG))]
9149   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9150 {
9151   switch (get_attr_type (insn))
9152     {
9153     case TYPE_LEA:
9154     case TYPE_ISHIFTX:
9155       return "#";
9156
9157     case TYPE_ALU:
9158       gcc_assert (operands[2] == const1_rtx);
9159       return "add{l}\t%k0, %k0";
9160
9161     default:
9162       if (operands[2] == const1_rtx
9163           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9164         return "sal{l}\t%k0";
9165       else
9166         return "sal{l}\t{%2, %k0|%k0, %2}";
9167     }
9168 }
9169   [(set_attr "isa" "*,*,bmi2")
9170    (set (attr "type")
9171      (cond [(eq_attr "alternative" "1")
9172               (const_string "lea")
9173             (eq_attr "alternative" "2")
9174               (const_string "ishiftx")
9175             (and (match_test "TARGET_DOUBLE_WITH_ADD")
9176                  (match_operand 2 "const1_operand" ""))
9177               (const_string "alu")
9178            ]
9179            (const_string "ishift")))
9180    (set (attr "length_immediate")
9181      (if_then_else
9182        (ior (eq_attr "type" "alu")
9183             (and (eq_attr "type" "ishift")
9184                  (and (match_operand 2 "const1_operand" "")
9185                       (ior (match_test "TARGET_SHIFT1")
9186                            (match_test "optimize_function_for_size_p (cfun)")))))
9187        (const_string "0")
9188        (const_string "*")))
9189    (set_attr "mode" "SI")])
9190
9191 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9192 (define_split
9193   [(set (match_operand:DI 0 "register_operand" "")
9194         (zero_extend:DI
9195           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
9196                      (match_operand:QI 2 "register_operand" ""))))
9197    (clobber (reg:CC FLAGS_REG))]
9198   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9199   [(set (match_dup 0)
9200         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9201   "operands[2] = gen_lowpart (SImode, operands[2]);")
9202
9203 (define_insn "*ashlhi3_1"
9204   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,Yp")
9205         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
9206                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
9207    (clobber (reg:CC FLAGS_REG))]
9208   "ix86_binary_operator_ok (ASHIFT, HImode, operands)"
9209 {
9210   switch (get_attr_type (insn))
9211     {
9212     case TYPE_LEA:
9213       return "#";
9214
9215     case TYPE_ALU:
9216       gcc_assert (operands[2] == const1_rtx);
9217       return "add{w}\t%0, %0";
9218
9219     default:
9220       if (operands[2] == const1_rtx
9221           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9222         return "sal{w}\t%0";
9223       else
9224         return "sal{w}\t{%2, %0|%0, %2}";
9225     }
9226 }
9227   [(set (attr "type")
9228      (cond [(eq_attr "alternative" "1")
9229               (const_string "lea")
9230             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9231                       (match_operand 0 "register_operand" ""))
9232                  (match_operand 2 "const1_operand" ""))
9233               (const_string "alu")
9234            ]
9235            (const_string "ishift")))
9236    (set (attr "length_immediate")
9237      (if_then_else
9238        (ior (eq_attr "type" "alu")
9239             (and (eq_attr "type" "ishift")
9240                  (and (match_operand 2 "const1_operand" "")
9241                       (ior (match_test "TARGET_SHIFT1")
9242                            (match_test "optimize_function_for_size_p (cfun)")))))
9243        (const_string "0")
9244        (const_string "*")))
9245    (set_attr "mode" "HI,SI")])
9246
9247 ;; %%% Potential partial reg stall on alternative 1.  What to do?
9248 (define_insn "*ashlqi3_1"
9249   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,Yp")
9250         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
9251                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
9252    (clobber (reg:CC FLAGS_REG))]
9253   "ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9254 {
9255   switch (get_attr_type (insn))
9256     {
9257     case TYPE_LEA:
9258       return "#";
9259
9260     case TYPE_ALU:
9261       gcc_assert (operands[2] == const1_rtx);
9262       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
9263         return "add{l}\t%k0, %k0";
9264       else
9265         return "add{b}\t%0, %0";
9266
9267     default:
9268       if (operands[2] == const1_rtx
9269           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9270         {
9271           if (get_attr_mode (insn) == MODE_SI)
9272             return "sal{l}\t%k0";
9273           else
9274             return "sal{b}\t%0";
9275         }
9276       else
9277         {
9278           if (get_attr_mode (insn) == MODE_SI)
9279             return "sal{l}\t{%2, %k0|%k0, %2}";
9280           else
9281             return "sal{b}\t{%2, %0|%0, %2}";
9282         }
9283     }
9284 }
9285   [(set (attr "type")
9286      (cond [(eq_attr "alternative" "2")
9287               (const_string "lea")
9288             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9289                       (match_operand 0 "register_operand" ""))
9290                  (match_operand 2 "const1_operand" ""))
9291               (const_string "alu")
9292            ]
9293            (const_string "ishift")))
9294    (set (attr "length_immediate")
9295      (if_then_else
9296        (ior (eq_attr "type" "alu")
9297             (and (eq_attr "type" "ishift")
9298                  (and (match_operand 2 "const1_operand" "")
9299                       (ior (match_test "TARGET_SHIFT1")
9300                            (match_test "optimize_function_for_size_p (cfun)")))))
9301        (const_string "0")
9302        (const_string "*")))
9303    (set_attr "mode" "QI,SI,SI")])
9304
9305 (define_insn "*ashlqi3_1_slp"
9306   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9307         (ashift:QI (match_dup 0)
9308                    (match_operand:QI 1 "nonmemory_operand" "cI")))
9309    (clobber (reg:CC FLAGS_REG))]
9310   "(optimize_function_for_size_p (cfun)
9311     || !TARGET_PARTIAL_FLAG_REG_STALL
9312     || (operands[1] == const1_rtx
9313         && (TARGET_SHIFT1
9314             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))"
9315 {
9316   switch (get_attr_type (insn))
9317     {
9318     case TYPE_ALU:
9319       gcc_assert (operands[1] == const1_rtx);
9320       return "add{b}\t%0, %0";
9321
9322     default:
9323       if (operands[1] == const1_rtx
9324           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9325         return "sal{b}\t%0";
9326       else
9327         return "sal{b}\t{%1, %0|%0, %1}";
9328     }
9329 }
9330   [(set (attr "type")
9331      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9332                       (match_operand 0 "register_operand" ""))
9333                  (match_operand 1 "const1_operand" ""))
9334               (const_string "alu")
9335            ]
9336            (const_string "ishift1")))
9337    (set (attr "length_immediate")
9338      (if_then_else
9339        (ior (eq_attr "type" "alu")
9340             (and (eq_attr "type" "ishift1")
9341                  (and (match_operand 1 "const1_operand" "")
9342                       (ior (match_test "TARGET_SHIFT1")
9343                            (match_test "optimize_function_for_size_p (cfun)")))))
9344        (const_string "0")
9345        (const_string "*")))
9346    (set_attr "mode" "QI")])
9347
9348 ;; Convert ashift to the lea pattern to avoid flags dependency.
9349 (define_split
9350   [(set (match_operand 0 "register_operand" "")
9351         (ashift (match_operand 1 "index_register_operand" "")
9352                 (match_operand:QI 2 "const_int_operand" "")))
9353    (clobber (reg:CC FLAGS_REG))]
9354   "GET_MODE (operands[0]) == GET_MODE (operands[1])
9355    && reload_completed
9356    && true_regnum (operands[0]) != true_regnum (operands[1])"
9357   [(const_int 0)]
9358 {
9359   enum machine_mode mode = GET_MODE (operands[0]);
9360   rtx pat;
9361
9362   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
9363     { 
9364       mode = SImode; 
9365       operands[0] = gen_lowpart (mode, operands[0]);
9366       operands[1] = gen_lowpart (mode, operands[1]);
9367     }
9368
9369   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), mode);
9370
9371   pat = gen_rtx_MULT (mode, operands[1], operands[2]);
9372
9373   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
9374   DONE;
9375 })
9376
9377 ;; Convert ashift to the lea pattern to avoid flags dependency.
9378 (define_split
9379   [(set (match_operand:DI 0 "register_operand" "")
9380         (zero_extend:DI
9381           (ashift:SI (match_operand:SI 1 "index_register_operand" "")
9382                      (match_operand:QI 2 "const_int_operand" ""))))
9383    (clobber (reg:CC FLAGS_REG))]
9384   "TARGET_64BIT && reload_completed
9385    && true_regnum (operands[0]) != true_regnum (operands[1])"
9386   [(set (match_dup 0)
9387         (zero_extend:DI (subreg:SI (mult:DI (match_dup 1) (match_dup 2)) 0)))]
9388 {
9389   operands[1] = gen_lowpart (DImode, operands[1]);
9390   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);
9391 })
9392
9393 ;; This pattern can't accept a variable shift count, since shifts by
9394 ;; zero don't affect the flags.  We assume that shifts by constant
9395 ;; zero are optimized away.
9396 (define_insn "*ashl<mode>3_cmp"
9397   [(set (reg FLAGS_REG)
9398         (compare
9399           (ashift:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")
9400                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9401           (const_int 0)))
9402    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9403         (ashift:SWI (match_dup 1) (match_dup 2)))]
9404   "(optimize_function_for_size_p (cfun)
9405     || !TARGET_PARTIAL_FLAG_REG_STALL
9406     || (operands[2] == const1_rtx
9407         && (TARGET_SHIFT1
9408             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
9409    && ix86_match_ccmode (insn, CCGOCmode)
9410    && ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9411 {
9412   switch (get_attr_type (insn))
9413     {
9414     case TYPE_ALU:
9415       gcc_assert (operands[2] == const1_rtx);
9416       return "add{<imodesuffix>}\t%0, %0";
9417
9418     default:
9419       if (operands[2] == const1_rtx
9420           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9421         return "sal{<imodesuffix>}\t%0";
9422       else
9423         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9424     }
9425 }
9426   [(set (attr "type")
9427      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9428                       (match_operand 0 "register_operand" ""))
9429                  (match_operand 2 "const1_operand" ""))
9430               (const_string "alu")
9431            ]
9432            (const_string "ishift")))
9433    (set (attr "length_immediate")
9434      (if_then_else
9435        (ior (eq_attr "type" "alu")
9436             (and (eq_attr "type" "ishift")
9437                  (and (match_operand 2 "const1_operand" "")
9438                       (ior (match_test "TARGET_SHIFT1")
9439                            (match_test "optimize_function_for_size_p (cfun)")))))
9440        (const_string "0")
9441        (const_string "*")))
9442    (set_attr "mode" "<MODE>")])
9443
9444 (define_insn "*ashlsi3_cmp_zext"
9445   [(set (reg FLAGS_REG)
9446         (compare
9447           (ashift:SI (match_operand:SI 1 "register_operand" "0")
9448                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
9449           (const_int 0)))
9450    (set (match_operand:DI 0 "register_operand" "=r")
9451         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9452   "TARGET_64BIT
9453    && (optimize_function_for_size_p (cfun)
9454        || !TARGET_PARTIAL_FLAG_REG_STALL
9455        || (operands[2] == const1_rtx
9456            && (TARGET_SHIFT1
9457                || TARGET_DOUBLE_WITH_ADD)))
9458    && ix86_match_ccmode (insn, CCGOCmode)
9459    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9460 {
9461   switch (get_attr_type (insn))
9462     {
9463     case TYPE_ALU:
9464       gcc_assert (operands[2] == const1_rtx);
9465       return "add{l}\t%k0, %k0";
9466
9467     default:
9468       if (operands[2] == const1_rtx
9469           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9470         return "sal{l}\t%k0";
9471       else
9472         return "sal{l}\t{%2, %k0|%k0, %2}";
9473     }
9474 }
9475   [(set (attr "type")
9476      (cond [(and (match_test "TARGET_DOUBLE_WITH_ADD")
9477                  (match_operand 2 "const1_operand" ""))
9478               (const_string "alu")
9479            ]
9480            (const_string "ishift")))
9481    (set (attr "length_immediate")
9482      (if_then_else
9483        (ior (eq_attr "type" "alu")
9484             (and (eq_attr "type" "ishift")
9485                  (and (match_operand 2 "const1_operand" "")
9486                       (ior (match_test "TARGET_SHIFT1")
9487                            (match_test "optimize_function_for_size_p (cfun)")))))
9488        (const_string "0")
9489        (const_string "*")))
9490    (set_attr "mode" "SI")])
9491
9492 (define_insn "*ashl<mode>3_cconly"
9493   [(set (reg FLAGS_REG)
9494         (compare
9495           (ashift:SWI (match_operand:SWI 1 "register_operand" "0")
9496                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9497           (const_int 0)))
9498    (clobber (match_scratch:SWI 0 "=<r>"))]
9499   "(optimize_function_for_size_p (cfun)
9500     || !TARGET_PARTIAL_FLAG_REG_STALL
9501     || (operands[2] == const1_rtx
9502         && (TARGET_SHIFT1
9503             || TARGET_DOUBLE_WITH_ADD)))
9504    && ix86_match_ccmode (insn, CCGOCmode)"
9505 {
9506   switch (get_attr_type (insn))
9507     {
9508     case TYPE_ALU:
9509       gcc_assert (operands[2] == const1_rtx);
9510       return "add{<imodesuffix>}\t%0, %0";
9511
9512     default:
9513       if (operands[2] == const1_rtx
9514           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9515         return "sal{<imodesuffix>}\t%0";
9516       else
9517         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9518     }
9519 }
9520   [(set (attr "type")
9521      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9522                       (match_operand 0 "register_operand" ""))
9523                  (match_operand 2 "const1_operand" ""))
9524               (const_string "alu")
9525            ]
9526            (const_string "ishift")))
9527    (set (attr "length_immediate")
9528      (if_then_else
9529        (ior (eq_attr "type" "alu")
9530             (and (eq_attr "type" "ishift")
9531                  (and (match_operand 2 "const1_operand" "")
9532                       (ior (match_test "TARGET_SHIFT1")
9533                            (match_test "optimize_function_for_size_p (cfun)")))))
9534        (const_string "0")
9535        (const_string "*")))
9536    (set_attr "mode" "<MODE>")])
9537
9538 ;; See comment above `ashl<mode>3' about how this works.
9539
9540 (define_expand "<shift_insn><mode>3"
9541   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
9542         (any_shiftrt:SDWIM (match_operand:SDWIM 1 "<shift_operand>" "")
9543                            (match_operand:QI 2 "nonmemory_operand" "")))]
9544   ""
9545   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
9546
9547 ;; Avoid useless masking of count operand.
9548 (define_insn_and_split "*<shift_insn><mode>3_mask"
9549   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9550         (any_shiftrt:SWI48
9551           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9552           (subreg:QI
9553             (and:SI
9554               (match_operand:SI 2 "nonimmediate_operand" "c")
9555               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9556    (clobber (reg:CC FLAGS_REG))]
9557   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
9558    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9559       == GET_MODE_BITSIZE (<MODE>mode)-1"
9560   "#"
9561   "&& 1"
9562   [(parallel [(set (match_dup 0)
9563                    (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))
9564               (clobber (reg:CC FLAGS_REG))])]
9565 {
9566   if (can_create_pseudo_p ())
9567     operands [2] = force_reg (SImode, operands[2]);
9568
9569   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9570 }
9571   [(set_attr "type" "ishift")
9572    (set_attr "mode" "<MODE>")])
9573
9574 (define_insn_and_split "*<shift_insn><mode>3_doubleword"
9575   [(set (match_operand:DWI 0 "register_operand" "=r")
9576         (any_shiftrt:DWI (match_operand:DWI 1 "register_operand" "0")
9577                          (match_operand:QI 2 "nonmemory_operand" "<S>c")))
9578    (clobber (reg:CC FLAGS_REG))]
9579   ""
9580   "#"
9581   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
9582   [(const_int 0)]
9583   "ix86_split_<shift_insn> (operands, NULL_RTX, <MODE>mode); DONE;"
9584   [(set_attr "type" "multi")])
9585
9586 ;; By default we don't ask for a scratch register, because when DWImode
9587 ;; values are manipulated, registers are already at a premium.  But if
9588 ;; we have one handy, we won't turn it away.
9589
9590 (define_peephole2
9591   [(match_scratch:DWIH 3 "r")
9592    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
9593                    (any_shiftrt:<DWI>
9594                      (match_operand:<DWI> 1 "register_operand" "")
9595                      (match_operand:QI 2 "nonmemory_operand" "")))
9596               (clobber (reg:CC FLAGS_REG))])
9597    (match_dup 3)]
9598   "TARGET_CMOVE"
9599   [(const_int 0)]
9600   "ix86_split_<shift_insn> (operands, operands[3], <DWI>mode); DONE;")
9601
9602 (define_insn "x86_64_shrd"
9603   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
9604         (ior:DI (ashiftrt:DI (match_dup 0)
9605                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
9606                 (ashift:DI (match_operand:DI 1 "register_operand" "r")
9607                   (minus:QI (const_int 64) (match_dup 2)))))
9608    (clobber (reg:CC FLAGS_REG))]
9609   "TARGET_64BIT"
9610   "shrd{q}\t{%s2%1, %0|%0, %1, %2}"
9611   [(set_attr "type" "ishift")
9612    (set_attr "prefix_0f" "1")
9613    (set_attr "mode" "DI")
9614    (set_attr "athlon_decode" "vector")
9615    (set_attr "amdfam10_decode" "vector")
9616    (set_attr "bdver1_decode" "vector")])
9617
9618 (define_insn "x86_shrd"
9619   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
9620         (ior:SI (ashiftrt:SI (match_dup 0)
9621                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
9622                 (ashift:SI (match_operand:SI 1 "register_operand" "r")
9623                   (minus:QI (const_int 32) (match_dup 2)))))
9624    (clobber (reg:CC FLAGS_REG))]
9625   ""
9626   "shrd{l}\t{%s2%1, %0|%0, %1, %2}"
9627   [(set_attr "type" "ishift")
9628    (set_attr "prefix_0f" "1")
9629    (set_attr "mode" "SI")
9630    (set_attr "pent_pair" "np")
9631    (set_attr "athlon_decode" "vector")
9632    (set_attr "amdfam10_decode" "vector")
9633    (set_attr "bdver1_decode" "vector")])
9634
9635 (define_insn "ashrdi3_cvt"
9636   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
9637         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
9638                      (match_operand:QI 2 "const_int_operand" "")))
9639    (clobber (reg:CC FLAGS_REG))]
9640   "TARGET_64BIT && INTVAL (operands[2]) == 63
9641    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9642    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
9643   "@
9644    {cqto|cqo}
9645    sar{q}\t{%2, %0|%0, %2}"
9646   [(set_attr "type" "imovx,ishift")
9647    (set_attr "prefix_0f" "0,*")
9648    (set_attr "length_immediate" "0,*")
9649    (set_attr "modrm" "0,1")
9650    (set_attr "mode" "DI")])
9651
9652 (define_insn "ashrsi3_cvt"
9653   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
9654         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
9655                      (match_operand:QI 2 "const_int_operand" "")))
9656    (clobber (reg:CC FLAGS_REG))]
9657   "INTVAL (operands[2]) == 31
9658    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9659    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9660   "@
9661    {cltd|cdq}
9662    sar{l}\t{%2, %0|%0, %2}"
9663   [(set_attr "type" "imovx,ishift")
9664    (set_attr "prefix_0f" "0,*")
9665    (set_attr "length_immediate" "0,*")
9666    (set_attr "modrm" "0,1")
9667    (set_attr "mode" "SI")])
9668
9669 (define_insn "*ashrsi3_cvt_zext"
9670   [(set (match_operand:DI 0 "register_operand" "=*d,r")
9671         (zero_extend:DI
9672           (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
9673                        (match_operand:QI 2 "const_int_operand" ""))))
9674    (clobber (reg:CC FLAGS_REG))]
9675   "TARGET_64BIT && INTVAL (operands[2]) == 31
9676    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9677    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9678   "@
9679    {cltd|cdq}
9680    sar{l}\t{%2, %k0|%k0, %2}"
9681   [(set_attr "type" "imovx,ishift")
9682    (set_attr "prefix_0f" "0,*")
9683    (set_attr "length_immediate" "0,*")
9684    (set_attr "modrm" "0,1")
9685    (set_attr "mode" "SI")])
9686
9687 (define_expand "x86_shift<mode>_adj_3"
9688   [(use (match_operand:SWI48 0 "register_operand" ""))
9689    (use (match_operand:SWI48 1 "register_operand" ""))
9690    (use (match_operand:QI 2 "register_operand" ""))]
9691   ""
9692 {
9693   rtx label = gen_label_rtx ();
9694   rtx tmp;
9695
9696   emit_insn (gen_testqi_ccz_1 (operands[2],
9697                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9698
9699   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9700   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9701   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9702                               gen_rtx_LABEL_REF (VOIDmode, label),
9703                               pc_rtx);
9704   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9705   JUMP_LABEL (tmp) = label;
9706
9707   emit_move_insn (operands[0], operands[1]);
9708   emit_insn (gen_ashr<mode>3_cvt (operands[1], operands[1],
9709                                   GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1)));
9710   emit_label (label);
9711   LABEL_NUSES (label) = 1;
9712
9713   DONE;
9714 })
9715
9716 (define_insn "*bmi2_<shift_insn><mode>3_1"
9717   [(set (match_operand:SWI48 0 "register_operand" "=r")
9718         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9719                            (match_operand:SWI48 2 "register_operand" "r")))]
9720   "TARGET_BMI2"
9721   "<shift>x\t{%2, %1, %0|%0, %1, %2}"
9722   [(set_attr "type" "ishiftx")
9723    (set_attr "mode" "<MODE>")])
9724
9725 (define_insn "*<shift_insn><mode>3_1"
9726   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
9727         (any_shiftrt:SWI48
9728           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
9729           (match_operand:QI 2 "nonmemory_operand" "c<S>,r")))
9730    (clobber (reg:CC FLAGS_REG))]
9731   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9732 {
9733   switch (get_attr_type (insn))
9734     {
9735     case TYPE_ISHIFTX:
9736       return "#";
9737
9738     default:
9739       if (operands[2] == const1_rtx
9740           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9741         return "<shift>{<imodesuffix>}\t%0";
9742       else
9743         return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9744     }
9745 }
9746   [(set_attr "isa" "*,bmi2")
9747    (set_attr "type" "ishift,ishiftx")
9748    (set (attr "length_immediate")
9749      (if_then_else
9750        (and (match_operand 2 "const1_operand" "")
9751             (ior (match_test "TARGET_SHIFT1")
9752                  (match_test "optimize_function_for_size_p (cfun)")))
9753        (const_string "0")
9754        (const_string "*")))
9755    (set_attr "mode" "<MODE>")])
9756
9757 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9758 (define_split
9759   [(set (match_operand:SWI48 0 "register_operand" "")
9760         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9761                            (match_operand:QI 2 "register_operand" "")))
9762    (clobber (reg:CC FLAGS_REG))]
9763   "TARGET_BMI2 && reload_completed"
9764   [(set (match_dup 0)
9765         (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))]
9766   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9767
9768 (define_insn "*bmi2_<shift_insn>si3_1_zext"
9769   [(set (match_operand:DI 0 "register_operand" "=r")
9770         (zero_extend:DI
9771           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9772                           (match_operand:SI 2 "register_operand" "r"))))]
9773   "TARGET_64BIT && TARGET_BMI2"
9774   "<shift>x\t{%2, %1, %k0|%k0, %1, %2}"
9775   [(set_attr "type" "ishiftx")
9776    (set_attr "mode" "SI")])
9777
9778 (define_insn "*<shift_insn>si3_1_zext"
9779   [(set (match_operand:DI 0 "register_operand" "=r,r")
9780         (zero_extend:DI
9781           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
9782                           (match_operand:QI 2 "nonmemory_operand" "cI,r"))))
9783    (clobber (reg:CC FLAGS_REG))]
9784   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9785 {
9786   switch (get_attr_type (insn))
9787     {
9788     case TYPE_ISHIFTX:
9789       return "#";
9790
9791     default:
9792       if (operands[2] == const1_rtx
9793           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9794         return "<shift>{l}\t%k0";
9795       else
9796         return "<shift>{l}\t{%2, %k0|%k0, %2}";
9797     }
9798 }
9799   [(set_attr "isa" "*,bmi2")
9800    (set_attr "type" "ishift,ishiftx")
9801    (set (attr "length_immediate")
9802      (if_then_else
9803        (and (match_operand 2 "const1_operand" "")
9804             (ior (match_test "TARGET_SHIFT1")
9805                  (match_test "optimize_function_for_size_p (cfun)")))
9806        (const_string "0")
9807        (const_string "*")))
9808    (set_attr "mode" "SI")])
9809
9810 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9811 (define_split
9812   [(set (match_operand:DI 0 "register_operand" "")
9813         (zero_extend:DI
9814           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
9815                           (match_operand:QI 2 "register_operand" ""))))
9816    (clobber (reg:CC FLAGS_REG))]
9817   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9818   [(set (match_dup 0)
9819         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9820   "operands[2] = gen_lowpart (SImode, operands[2]);")
9821
9822 (define_insn "*<shift_insn><mode>3_1"
9823   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
9824         (any_shiftrt:SWI12
9825           (match_operand:SWI12 1 "nonimmediate_operand" "0")
9826           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
9827    (clobber (reg:CC FLAGS_REG))]
9828   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9829 {
9830   if (operands[2] == const1_rtx
9831       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9832     return "<shift>{<imodesuffix>}\t%0";
9833   else
9834     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9835 }
9836   [(set_attr "type" "ishift")
9837    (set (attr "length_immediate")
9838      (if_then_else
9839        (and (match_operand 2 "const1_operand" "")
9840             (ior (match_test "TARGET_SHIFT1")
9841                  (match_test "optimize_function_for_size_p (cfun)")))
9842        (const_string "0")
9843        (const_string "*")))
9844    (set_attr "mode" "<MODE>")])
9845
9846 (define_insn "*<shift_insn>qi3_1_slp"
9847   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9848         (any_shiftrt:QI (match_dup 0)
9849                         (match_operand:QI 1 "nonmemory_operand" "cI")))
9850    (clobber (reg:CC FLAGS_REG))]
9851   "(optimize_function_for_size_p (cfun)
9852     || !TARGET_PARTIAL_REG_STALL
9853     || (operands[1] == const1_rtx
9854         && TARGET_SHIFT1))"
9855 {
9856   if (operands[1] == const1_rtx
9857       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9858     return "<shift>{b}\t%0";
9859   else
9860     return "<shift>{b}\t{%1, %0|%0, %1}";
9861 }
9862   [(set_attr "type" "ishift1")
9863    (set (attr "length_immediate")
9864      (if_then_else
9865        (and (match_operand 1 "const1_operand" "")
9866             (ior (match_test "TARGET_SHIFT1")
9867                  (match_test "optimize_function_for_size_p (cfun)")))
9868        (const_string "0")
9869        (const_string "*")))
9870    (set_attr "mode" "QI")])
9871
9872 ;; This pattern can't accept a variable shift count, since shifts by
9873 ;; zero don't affect the flags.  We assume that shifts by constant
9874 ;; zero are optimized away.
9875 (define_insn "*<shift_insn><mode>3_cmp"
9876   [(set (reg FLAGS_REG)
9877         (compare
9878           (any_shiftrt:SWI
9879             (match_operand:SWI 1 "nonimmediate_operand" "0")
9880             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9881           (const_int 0)))
9882    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9883         (any_shiftrt:SWI (match_dup 1) (match_dup 2)))]
9884   "(optimize_function_for_size_p (cfun)
9885     || !TARGET_PARTIAL_FLAG_REG_STALL
9886     || (operands[2] == const1_rtx
9887         && TARGET_SHIFT1))
9888    && ix86_match_ccmode (insn, CCGOCmode)
9889    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9890 {
9891   if (operands[2] == const1_rtx
9892       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9893     return "<shift>{<imodesuffix>}\t%0";
9894   else
9895     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9896 }
9897   [(set_attr "type" "ishift")
9898    (set (attr "length_immediate")
9899      (if_then_else
9900        (and (match_operand 2 "const1_operand" "")
9901             (ior (match_test "TARGET_SHIFT1")
9902                  (match_test "optimize_function_for_size_p (cfun)")))
9903        (const_string "0")
9904        (const_string "*")))
9905    (set_attr "mode" "<MODE>")])
9906
9907 (define_insn "*<shift_insn>si3_cmp_zext"
9908   [(set (reg FLAGS_REG)
9909         (compare
9910           (any_shiftrt:SI (match_operand:SI 1 "register_operand" "0")
9911                           (match_operand:QI 2 "const_1_to_31_operand" "I"))
9912           (const_int 0)))
9913    (set (match_operand:DI 0 "register_operand" "=r")
9914         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9915   "TARGET_64BIT
9916    && (optimize_function_for_size_p (cfun)
9917        || !TARGET_PARTIAL_FLAG_REG_STALL
9918        || (operands[2] == const1_rtx
9919            && TARGET_SHIFT1))
9920    && ix86_match_ccmode (insn, CCGOCmode)
9921    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9922 {
9923   if (operands[2] == const1_rtx
9924       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9925     return "<shift>{l}\t%k0";
9926   else
9927     return "<shift>{l}\t{%2, %k0|%k0, %2}";
9928 }
9929   [(set_attr "type" "ishift")
9930    (set (attr "length_immediate")
9931      (if_then_else
9932        (and (match_operand 2 "const1_operand" "")
9933             (ior (match_test "TARGET_SHIFT1")
9934                  (match_test "optimize_function_for_size_p (cfun)")))
9935        (const_string "0")
9936        (const_string "*")))
9937    (set_attr "mode" "SI")])
9938
9939 (define_insn "*<shift_insn><mode>3_cconly"
9940   [(set (reg FLAGS_REG)
9941         (compare
9942           (any_shiftrt:SWI
9943             (match_operand:SWI 1 "register_operand" "0")
9944             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9945           (const_int 0)))
9946    (clobber (match_scratch:SWI 0 "=<r>"))]
9947   "(optimize_function_for_size_p (cfun)
9948     || !TARGET_PARTIAL_FLAG_REG_STALL
9949     || (operands[2] == const1_rtx
9950         && TARGET_SHIFT1))
9951    && ix86_match_ccmode (insn, CCGOCmode)"
9952 {
9953   if (operands[2] == const1_rtx
9954       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9955     return "<shift>{<imodesuffix>}\t%0";
9956   else
9957     return "<shift>{<imodesuffix>}\t{%2, %0|%0, %2}";
9958 }
9959   [(set_attr "type" "ishift")
9960    (set (attr "length_immediate")
9961      (if_then_else
9962        (and (match_operand 2 "const1_operand" "")
9963             (ior (match_test "TARGET_SHIFT1")
9964                  (match_test "optimize_function_for_size_p (cfun)")))
9965        (const_string "0")
9966        (const_string "*")))
9967    (set_attr "mode" "<MODE>")])
9968 \f
9969 ;; Rotate instructions
9970
9971 (define_expand "<rotate_insn>ti3"
9972   [(set (match_operand:TI 0 "register_operand" "")
9973         (any_rotate:TI (match_operand:TI 1 "register_operand" "")
9974                        (match_operand:QI 2 "nonmemory_operand" "")))]
9975   "TARGET_64BIT"
9976 {
9977   if (const_1_to_63_operand (operands[2], VOIDmode))
9978     emit_insn (gen_ix86_<rotate_insn>ti3_doubleword
9979                 (operands[0], operands[1], operands[2]));
9980   else
9981     FAIL;
9982
9983   DONE;
9984 })
9985
9986 (define_expand "<rotate_insn>di3"
9987   [(set (match_operand:DI 0 "shiftdi_operand" "")
9988         (any_rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
9989                        (match_operand:QI 2 "nonmemory_operand" "")))]
9990  ""
9991 {
9992   if (TARGET_64BIT)
9993     ix86_expand_binary_operator (<CODE>, DImode, operands);
9994   else if (const_1_to_31_operand (operands[2], VOIDmode))
9995     emit_insn (gen_ix86_<rotate_insn>di3_doubleword
9996                 (operands[0], operands[1], operands[2]));
9997   else
9998     FAIL;
9999
10000   DONE;
10001 })
10002
10003 (define_expand "<rotate_insn><mode>3"
10004   [(set (match_operand:SWIM124 0 "nonimmediate_operand" "")
10005         (any_rotate:SWIM124 (match_operand:SWIM124 1 "nonimmediate_operand" "")
10006                             (match_operand:QI 2 "nonmemory_operand" "")))]
10007   ""
10008   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
10009
10010 ;; Avoid useless masking of count operand.
10011 (define_insn_and_split "*<rotate_insn><mode>3_mask"
10012   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
10013         (any_rotate:SWI48
10014           (match_operand:SWI48 1 "nonimmediate_operand" "0")
10015           (subreg:QI
10016             (and:SI
10017               (match_operand:SI 2 "nonimmediate_operand" "c")
10018               (match_operand:SI 3 "const_int_operand" "n")) 0)))
10019    (clobber (reg:CC FLAGS_REG))]
10020   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
10021    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10022       == GET_MODE_BITSIZE (<MODE>mode)-1"
10023   "#"
10024   "&& 1"
10025   [(parallel [(set (match_dup 0)
10026                    (any_rotate:SWI48 (match_dup 1) (match_dup 2)))
10027               (clobber (reg:CC FLAGS_REG))])]
10028 {
10029   if (can_create_pseudo_p ())
10030     operands [2] = force_reg (SImode, operands[2]);
10031
10032   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
10033 }
10034   [(set_attr "type" "rotate")
10035    (set_attr "mode" "<MODE>")])
10036
10037 ;; Implement rotation using two double-precision
10038 ;; shift instructions and a scratch register.
10039
10040 (define_insn_and_split "ix86_rotl<dwi>3_doubleword"
10041  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10042        (rotate:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10043                      (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10044   (clobber (reg:CC FLAGS_REG))
10045   (clobber (match_scratch:DWIH 3 "=&r"))]
10046  ""
10047  "#"
10048  "reload_completed"
10049  [(set (match_dup 3) (match_dup 4))
10050   (parallel
10051    [(set (match_dup 4)
10052          (ior:DWIH (ashift:DWIH (match_dup 4) (match_dup 2))
10053                    (lshiftrt:DWIH (match_dup 5)
10054                                   (minus:QI (match_dup 6) (match_dup 2)))))
10055     (clobber (reg:CC FLAGS_REG))])
10056   (parallel
10057    [(set (match_dup 5)
10058          (ior:DWIH (ashift:DWIH (match_dup 5) (match_dup 2))
10059                    (lshiftrt:DWIH (match_dup 3)
10060                                   (minus:QI (match_dup 6) (match_dup 2)))))
10061     (clobber (reg:CC FLAGS_REG))])]
10062 {
10063   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10064
10065   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10066 })
10067
10068 (define_insn_and_split "ix86_rotr<dwi>3_doubleword"
10069  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10070        (rotatert:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10071                        (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10072   (clobber (reg:CC FLAGS_REG))
10073   (clobber (match_scratch:DWIH 3 "=&r"))]
10074  ""
10075  "#"
10076  "reload_completed"
10077  [(set (match_dup 3) (match_dup 4))
10078   (parallel
10079    [(set (match_dup 4)
10080          (ior:DWIH (ashiftrt:DWIH (match_dup 4) (match_dup 2))
10081                    (ashift:DWIH (match_dup 5)
10082                                 (minus:QI (match_dup 6) (match_dup 2)))))
10083     (clobber (reg:CC FLAGS_REG))])
10084   (parallel
10085    [(set (match_dup 5)
10086          (ior:DWIH (ashiftrt:DWIH (match_dup 5) (match_dup 2))
10087                    (ashift:DWIH (match_dup 3)
10088                                 (minus:QI (match_dup 6) (match_dup 2)))))
10089     (clobber (reg:CC FLAGS_REG))])]
10090 {
10091   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10092
10093   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10094 })
10095
10096 (define_insn "*bmi2_rorx<mode>3_1"
10097   [(set (match_operand:SWI48 0 "register_operand" "=r")
10098         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
10099                         (match_operand:QI 2 "immediate_operand" "<S>")))]
10100   "TARGET_BMI2"
10101   "rorx\t{%2, %1, %0|%0, %1, %2}"
10102   [(set_attr "type" "rotatex")
10103    (set_attr "mode" "<MODE>")])
10104
10105 (define_insn "*<rotate_insn><mode>3_1"
10106   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
10107         (any_rotate:SWI48
10108           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
10109           (match_operand:QI 2 "nonmemory_operand" "c<S>,<S>")))
10110    (clobber (reg:CC FLAGS_REG))]
10111   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10112 {
10113   switch (get_attr_type (insn))
10114     {
10115     case TYPE_ROTATEX:
10116       return "#";
10117
10118     default:
10119       if (operands[2] == const1_rtx
10120           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10121         return "<rotate>{<imodesuffix>}\t%0";
10122       else
10123         return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10124     }
10125 }
10126   [(set_attr "isa" "*,bmi2")
10127    (set_attr "type" "rotate,rotatex")
10128    (set (attr "length_immediate")
10129      (if_then_else
10130        (and (eq_attr "type" "rotate")
10131             (and (match_operand 2 "const1_operand" "")
10132                  (ior (match_test "TARGET_SHIFT1")
10133                       (match_test "optimize_function_for_size_p (cfun)"))))
10134        (const_string "0")
10135        (const_string "*")))
10136    (set_attr "mode" "<MODE>")])
10137
10138 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10139 (define_split
10140   [(set (match_operand:SWI48 0 "register_operand" "")
10141         (rotate:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10142                       (match_operand:QI 2 "immediate_operand" "")))
10143    (clobber (reg:CC FLAGS_REG))]
10144   "TARGET_BMI2 && reload_completed"
10145   [(set (match_dup 0)
10146         (rotatert:SWI48 (match_dup 1) (match_dup 2)))]
10147 {
10148   operands[2]
10149     = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - INTVAL (operands[2]));
10150 })
10151
10152 (define_split
10153   [(set (match_operand:SWI48 0 "register_operand" "")
10154         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10155                         (match_operand:QI 2 "immediate_operand" "")))
10156    (clobber (reg:CC FLAGS_REG))]
10157   "TARGET_BMI2 && reload_completed"
10158   [(set (match_dup 0)
10159         (rotatert:SWI48 (match_dup 1) (match_dup 2)))])
10160
10161 (define_insn "*bmi2_rorxsi3_1_zext"
10162   [(set (match_operand:DI 0 "register_operand" "=r")
10163         (zero_extend:DI
10164           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
10165                        (match_operand:QI 2 "immediate_operand" "I"))))]
10166   "TARGET_64BIT && TARGET_BMI2"
10167   "rorx\t{%2, %1, %k0|%k0, %1, %2}"
10168   [(set_attr "type" "rotatex")
10169    (set_attr "mode" "SI")])
10170
10171 (define_insn "*<rotate_insn>si3_1_zext"
10172   [(set (match_operand:DI 0 "register_operand" "=r,r")
10173         (zero_extend:DI
10174           (any_rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
10175                          (match_operand:QI 2 "nonmemory_operand" "cI,I"))))
10176    (clobber (reg:CC FLAGS_REG))]
10177   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
10178 {
10179   switch (get_attr_type (insn))
10180     {
10181     case TYPE_ROTATEX:
10182       return "#";
10183
10184     default:
10185       if (operands[2] == const1_rtx
10186           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10187         return "<rotate>{l}\t%k0";
10188       else
10189         return "<rotate>{l}\t{%2, %k0|%k0, %2}";
10190     }
10191 }
10192   [(set_attr "isa" "*,bmi2")
10193    (set_attr "type" "rotate,rotatex")
10194    (set (attr "length_immediate")
10195      (if_then_else
10196        (and (eq_attr "type" "rotate")
10197             (and (match_operand 2 "const1_operand" "")
10198                  (ior (match_test "TARGET_SHIFT1")
10199                       (match_test "optimize_function_for_size_p (cfun)"))))
10200        (const_string "0")
10201        (const_string "*")))
10202    (set_attr "mode" "SI")])
10203
10204 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10205 (define_split
10206   [(set (match_operand:DI 0 "register_operand" "")
10207         (zero_extend:DI
10208           (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
10209                      (match_operand:QI 2 "immediate_operand" ""))))
10210    (clobber (reg:CC FLAGS_REG))]
10211   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10212   [(set (match_dup 0)
10213         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))]
10214 {
10215   operands[2]
10216     = GEN_INT (GET_MODE_BITSIZE (SImode) - INTVAL (operands[2]));
10217 })
10218
10219 (define_split
10220   [(set (match_operand:DI 0 "register_operand" "")
10221         (zero_extend:DI
10222           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
10223                        (match_operand:QI 2 "immediate_operand" ""))))
10224    (clobber (reg:CC FLAGS_REG))]
10225   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10226   [(set (match_dup 0)
10227         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))])
10228
10229 (define_insn "*<rotate_insn><mode>3_1"
10230   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
10231         (any_rotate:SWI12 (match_operand:SWI12 1 "nonimmediate_operand" "0")
10232                           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
10233    (clobber (reg:CC FLAGS_REG))]
10234   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10235 {
10236   if (operands[2] == const1_rtx
10237       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10238     return "<rotate>{<imodesuffix>}\t%0";
10239   else
10240     return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10241 }
10242   [(set_attr "type" "rotate")
10243    (set (attr "length_immediate")
10244      (if_then_else
10245        (and (match_operand 2 "const1_operand" "")
10246             (ior (match_test "TARGET_SHIFT1")
10247                  (match_test "optimize_function_for_size_p (cfun)")))
10248        (const_string "0")
10249        (const_string "*")))
10250    (set_attr "mode" "<MODE>")])
10251
10252 (define_insn "*<rotate_insn>qi3_1_slp"
10253   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10254         (any_rotate:QI (match_dup 0)
10255                        (match_operand:QI 1 "nonmemory_operand" "cI")))
10256    (clobber (reg:CC FLAGS_REG))]
10257   "(optimize_function_for_size_p (cfun)
10258     || !TARGET_PARTIAL_REG_STALL
10259     || (operands[1] == const1_rtx
10260         && TARGET_SHIFT1))"
10261 {
10262   if (operands[1] == const1_rtx
10263       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10264     return "<rotate>{b}\t%0";
10265   else
10266     return "<rotate>{b}\t{%1, %0|%0, %1}";
10267 }
10268   [(set_attr "type" "rotate1")
10269    (set (attr "length_immediate")
10270      (if_then_else
10271        (and (match_operand 1 "const1_operand" "")
10272             (ior (match_test "TARGET_SHIFT1")
10273                  (match_test "optimize_function_for_size_p (cfun)")))
10274        (const_string "0")
10275        (const_string "*")))
10276    (set_attr "mode" "QI")])
10277
10278 (define_split
10279  [(set (match_operand:HI 0 "register_operand" "")
10280        (any_rotate:HI (match_dup 0) (const_int 8)))
10281   (clobber (reg:CC FLAGS_REG))]
10282  "reload_completed
10283   && (TARGET_USE_XCHGB || optimize_function_for_size_p (cfun))"
10284  [(parallel [(set (strict_low_part (match_dup 0))
10285                   (bswap:HI (match_dup 0)))
10286              (clobber (reg:CC FLAGS_REG))])])
10287 \f
10288 ;; Bit set / bit test instructions
10289
10290 (define_expand "extv"
10291   [(set (match_operand:SI 0 "register_operand" "")
10292         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
10293                          (match_operand:SI 2 "const8_operand" "")
10294                          (match_operand:SI 3 "const8_operand" "")))]
10295   ""
10296 {
10297   /* Handle extractions from %ah et al.  */
10298   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10299     FAIL;
10300
10301   /* From mips.md: extract_bit_field doesn't verify that our source
10302      matches the predicate, so check it again here.  */
10303   if (! ext_register_operand (operands[1], VOIDmode))
10304     FAIL;
10305 })
10306
10307 (define_expand "extzv"
10308   [(set (match_operand:SI 0 "register_operand" "")
10309         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
10310                          (match_operand:SI 2 "const8_operand" "")
10311                          (match_operand:SI 3 "const8_operand" "")))]
10312   ""
10313 {
10314   /* Handle extractions from %ah et al.  */
10315   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10316     FAIL;
10317
10318   /* From mips.md: extract_bit_field doesn't verify that our source
10319      matches the predicate, so check it again here.  */
10320   if (! ext_register_operand (operands[1], VOIDmode))
10321     FAIL;
10322 })
10323
10324 (define_expand "insv"
10325   [(set (zero_extract (match_operand 0 "register_operand" "")
10326                       (match_operand 1 "const_int_operand" "")
10327                       (match_operand 2 "const_int_operand" ""))
10328         (match_operand 3 "register_operand" ""))]
10329   ""
10330 {
10331   rtx (*gen_mov_insv_1) (rtx, rtx);
10332
10333   if (ix86_expand_pinsr (operands))
10334     DONE;
10335
10336   /* Handle insertions to %ah et al.  */
10337   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
10338     FAIL;
10339
10340   /* From mips.md: insert_bit_field doesn't verify that our source
10341      matches the predicate, so check it again here.  */
10342   if (! ext_register_operand (operands[0], VOIDmode))
10343     FAIL;
10344
10345   gen_mov_insv_1 = (TARGET_64BIT
10346                     ? gen_movdi_insv_1 : gen_movsi_insv_1);
10347
10348   emit_insn (gen_mov_insv_1 (operands[0], operands[3]));
10349   DONE;
10350 })
10351
10352 ;; %%% bts, btr, btc, bt.
10353 ;; In general these instructions are *slow* when applied to memory,
10354 ;; since they enforce atomic operation.  When applied to registers,
10355 ;; it depends on the cpu implementation.  They're never faster than
10356 ;; the corresponding and/ior/xor operations, so with 32-bit there's
10357 ;; no point.  But in 64-bit, we can't hold the relevant immediates
10358 ;; within the instruction itself, so operating on bits in the high
10359 ;; 32-bits of a register becomes easier.
10360 ;;
10361 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
10362 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
10363 ;; negdf respectively, so they can never be disabled entirely.
10364
10365 (define_insn "*btsq"
10366   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10367                          (const_int 1)
10368                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10369         (const_int 1))
10370    (clobber (reg:CC FLAGS_REG))]
10371   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10372   "bts{q}\t{%1, %0|%0, %1}"
10373   [(set_attr "type" "alu1")
10374    (set_attr "prefix_0f" "1")
10375    (set_attr "mode" "DI")])
10376
10377 (define_insn "*btrq"
10378   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10379                          (const_int 1)
10380                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10381         (const_int 0))
10382    (clobber (reg:CC FLAGS_REG))]
10383   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10384   "btr{q}\t{%1, %0|%0, %1}"
10385   [(set_attr "type" "alu1")
10386    (set_attr "prefix_0f" "1")
10387    (set_attr "mode" "DI")])
10388
10389 (define_insn "*btcq"
10390   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10391                          (const_int 1)
10392                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10393         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
10394    (clobber (reg:CC FLAGS_REG))]
10395   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10396   "btc{q}\t{%1, %0|%0, %1}"
10397   [(set_attr "type" "alu1")
10398    (set_attr "prefix_0f" "1")
10399    (set_attr "mode" "DI")])
10400
10401 ;; Allow Nocona to avoid these instructions if a register is available.
10402
10403 (define_peephole2
10404   [(match_scratch:DI 2 "r")
10405    (parallel [(set (zero_extract:DI
10406                      (match_operand:DI 0 "register_operand" "")
10407                      (const_int 1)
10408                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10409                    (const_int 1))
10410               (clobber (reg:CC FLAGS_REG))])]
10411   "TARGET_64BIT && !TARGET_USE_BT"
10412   [(const_int 0)]
10413 {
10414   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10415   rtx op1;
10416
10417   if (HOST_BITS_PER_WIDE_INT >= 64)
10418     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10419   else if (i < HOST_BITS_PER_WIDE_INT)
10420     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10421   else
10422     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10423
10424   op1 = immed_double_const (lo, hi, DImode);
10425   if (i >= 31)
10426     {
10427       emit_move_insn (operands[2], op1);
10428       op1 = operands[2];
10429     }
10430
10431   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
10432   DONE;
10433 })
10434
10435 (define_peephole2
10436   [(match_scratch:DI 2 "r")
10437    (parallel [(set (zero_extract:DI
10438                      (match_operand:DI 0 "register_operand" "")
10439                      (const_int 1)
10440                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10441                    (const_int 0))
10442               (clobber (reg:CC FLAGS_REG))])]
10443   "TARGET_64BIT && !TARGET_USE_BT"
10444   [(const_int 0)]
10445 {
10446   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10447   rtx op1;
10448
10449   if (HOST_BITS_PER_WIDE_INT >= 64)
10450     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10451   else if (i < HOST_BITS_PER_WIDE_INT)
10452     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10453   else
10454     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10455
10456   op1 = immed_double_const (~lo, ~hi, DImode);
10457   if (i >= 32)
10458     {
10459       emit_move_insn (operands[2], op1);
10460       op1 = operands[2];
10461     }
10462
10463   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
10464   DONE;
10465 })
10466
10467 (define_peephole2
10468   [(match_scratch:DI 2 "r")
10469    (parallel [(set (zero_extract:DI
10470                      (match_operand:DI 0 "register_operand" "")
10471                      (const_int 1)
10472                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10473               (not:DI (zero_extract:DI
10474                         (match_dup 0) (const_int 1) (match_dup 1))))
10475               (clobber (reg:CC FLAGS_REG))])]
10476   "TARGET_64BIT && !TARGET_USE_BT"
10477   [(const_int 0)]
10478 {
10479   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10480   rtx op1;
10481
10482   if (HOST_BITS_PER_WIDE_INT >= 64)
10483     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10484   else if (i < HOST_BITS_PER_WIDE_INT)
10485     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10486   else
10487     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10488
10489   op1 = immed_double_const (lo, hi, DImode);
10490   if (i >= 31)
10491     {
10492       emit_move_insn (operands[2], op1);
10493       op1 = operands[2];
10494     }
10495
10496   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
10497   DONE;
10498 })
10499
10500 (define_insn "*bt<mode>"
10501   [(set (reg:CCC FLAGS_REG)
10502         (compare:CCC
10503           (zero_extract:SWI48
10504             (match_operand:SWI48 0 "register_operand" "r")
10505             (const_int 1)
10506             (match_operand:SWI48 1 "x86_64_nonmemory_operand" "rN"))
10507           (const_int 0)))]
10508   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10509   "bt{<imodesuffix>}\t{%1, %0|%0, %1}"
10510   [(set_attr "type" "alu1")
10511    (set_attr "prefix_0f" "1")
10512    (set_attr "mode" "<MODE>")])
10513 \f
10514 ;; Store-flag instructions.
10515
10516 ;; For all sCOND expanders, also expand the compare or test insn that
10517 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
10518
10519 (define_insn_and_split "*setcc_di_1"
10520   [(set (match_operand:DI 0 "register_operand" "=q")
10521         (match_operator:DI 1 "ix86_comparison_operator"
10522           [(reg FLAGS_REG) (const_int 0)]))]
10523   "TARGET_64BIT && !TARGET_PARTIAL_REG_STALL"
10524   "#"
10525   "&& reload_completed"
10526   [(set (match_dup 2) (match_dup 1))
10527    (set (match_dup 0) (zero_extend:DI (match_dup 2)))]
10528 {
10529   PUT_MODE (operands[1], QImode);
10530   operands[2] = gen_lowpart (QImode, operands[0]);
10531 })
10532
10533 (define_insn_and_split "*setcc_si_1_and"
10534   [(set (match_operand:SI 0 "register_operand" "=q")
10535         (match_operator:SI 1 "ix86_comparison_operator"
10536           [(reg FLAGS_REG) (const_int 0)]))
10537    (clobber (reg:CC FLAGS_REG))]
10538   "!TARGET_PARTIAL_REG_STALL
10539    && TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
10540   "#"
10541   "&& reload_completed"
10542   [(set (match_dup 2) (match_dup 1))
10543    (parallel [(set (match_dup 0) (zero_extend:SI (match_dup 2)))
10544               (clobber (reg:CC FLAGS_REG))])]
10545 {
10546   PUT_MODE (operands[1], QImode);
10547   operands[2] = gen_lowpart (QImode, operands[0]);
10548 })
10549
10550 (define_insn_and_split "*setcc_si_1_movzbl"
10551   [(set (match_operand:SI 0 "register_operand" "=q")
10552         (match_operator:SI 1 "ix86_comparison_operator"
10553           [(reg FLAGS_REG) (const_int 0)]))]
10554   "!TARGET_PARTIAL_REG_STALL
10555    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
10556   "#"
10557   "&& reload_completed"
10558   [(set (match_dup 2) (match_dup 1))
10559    (set (match_dup 0) (zero_extend:SI (match_dup 2)))]
10560 {
10561   PUT_MODE (operands[1], QImode);
10562   operands[2] = gen_lowpart (QImode, operands[0]);
10563 })
10564
10565 (define_insn "*setcc_qi"
10566   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10567         (match_operator:QI 1 "ix86_comparison_operator"
10568           [(reg FLAGS_REG) (const_int 0)]))]
10569   ""
10570   "set%C1\t%0"
10571   [(set_attr "type" "setcc")
10572    (set_attr "mode" "QI")])
10573
10574 (define_insn "*setcc_qi_slp"
10575   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10576         (match_operator:QI 1 "ix86_comparison_operator"
10577           [(reg FLAGS_REG) (const_int 0)]))]
10578   ""
10579   "set%C1\t%0"
10580   [(set_attr "type" "setcc")
10581    (set_attr "mode" "QI")])
10582
10583 ;; In general it is not safe to assume too much about CCmode registers,
10584 ;; so simplify-rtx stops when it sees a second one.  Under certain
10585 ;; conditions this is safe on x86, so help combine not create
10586 ;;
10587 ;;      seta    %al
10588 ;;      testb   %al, %al
10589 ;;      sete    %al
10590
10591 (define_split
10592   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10593         (ne:QI (match_operator 1 "ix86_comparison_operator"
10594                  [(reg FLAGS_REG) (const_int 0)])
10595             (const_int 0)))]
10596   ""
10597   [(set (match_dup 0) (match_dup 1))]
10598   "PUT_MODE (operands[1], QImode);")
10599
10600 (define_split
10601   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10602         (ne:QI (match_operator 1 "ix86_comparison_operator"
10603                  [(reg FLAGS_REG) (const_int 0)])
10604             (const_int 0)))]
10605   ""
10606   [(set (match_dup 0) (match_dup 1))]
10607   "PUT_MODE (operands[1], QImode);")
10608
10609 (define_split
10610   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10611         (eq:QI (match_operator 1 "ix86_comparison_operator"
10612                  [(reg FLAGS_REG) (const_int 0)])
10613             (const_int 0)))]
10614   ""
10615   [(set (match_dup 0) (match_dup 1))]
10616 {
10617   rtx new_op1 = copy_rtx (operands[1]);
10618   operands[1] = new_op1;
10619   PUT_MODE (new_op1, QImode);
10620   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10621                                              GET_MODE (XEXP (new_op1, 0))));
10622
10623   /* Make sure that (a) the CCmode we have for the flags is strong
10624      enough for the reversed compare or (b) we have a valid FP compare.  */
10625   if (! ix86_comparison_operator (new_op1, VOIDmode))
10626     FAIL;
10627 })
10628
10629 (define_split
10630   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10631         (eq:QI (match_operator 1 "ix86_comparison_operator"
10632                  [(reg FLAGS_REG) (const_int 0)])
10633             (const_int 0)))]
10634   ""
10635   [(set (match_dup 0) (match_dup 1))]
10636 {
10637   rtx new_op1 = copy_rtx (operands[1]);
10638   operands[1] = new_op1;
10639   PUT_MODE (new_op1, QImode);
10640   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10641                                              GET_MODE (XEXP (new_op1, 0))));
10642
10643   /* Make sure that (a) the CCmode we have for the flags is strong
10644      enough for the reversed compare or (b) we have a valid FP compare.  */
10645   if (! ix86_comparison_operator (new_op1, VOIDmode))
10646     FAIL;
10647 })
10648
10649 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
10650 ;; subsequent logical operations are used to imitate conditional moves.
10651 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
10652 ;; it directly.
10653
10654 (define_insn "setcc_<mode>_sse"
10655   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
10656         (match_operator:MODEF 3 "sse_comparison_operator"
10657           [(match_operand:MODEF 1 "register_operand" "0,x")
10658            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
10659   "SSE_FLOAT_MODE_P (<MODE>mode)"
10660   "@
10661    cmp%D3<ssemodesuffix>\t{%2, %0|%0, %2}
10662    vcmp%D3<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
10663   [(set_attr "isa" "noavx,avx")
10664    (set_attr "type" "ssecmp")
10665    (set_attr "length_immediate" "1")
10666    (set_attr "prefix" "orig,vex")
10667    (set_attr "mode" "<MODE>")])
10668 \f
10669 ;; Basic conditional jump instructions.
10670 ;; We ignore the overflow flag for signed branch instructions.
10671
10672 (define_insn "*jcc_1"
10673   [(set (pc)
10674         (if_then_else (match_operator 1 "ix86_comparison_operator"
10675                                       [(reg FLAGS_REG) (const_int 0)])
10676                       (label_ref (match_operand 0 "" ""))
10677                       (pc)))]
10678   ""
10679   "%+j%C1\t%l0"
10680   [(set_attr "type" "ibr")
10681    (set_attr "modrm" "0")
10682    (set (attr "length")
10683            (if_then_else (and (ge (minus (match_dup 0) (pc))
10684                                   (const_int -126))
10685                               (lt (minus (match_dup 0) (pc))
10686                                   (const_int 128)))
10687              (const_int 2)
10688              (const_int 6)))])
10689
10690 (define_insn "*jcc_2"
10691   [(set (pc)
10692         (if_then_else (match_operator 1 "ix86_comparison_operator"
10693                                       [(reg FLAGS_REG) (const_int 0)])
10694                       (pc)
10695                       (label_ref (match_operand 0 "" ""))))]
10696   ""
10697   "%+j%c1\t%l0"
10698   [(set_attr "type" "ibr")
10699    (set_attr "modrm" "0")
10700    (set (attr "length")
10701            (if_then_else (and (ge (minus (match_dup 0) (pc))
10702                                   (const_int -126))
10703                               (lt (minus (match_dup 0) (pc))
10704                                   (const_int 128)))
10705              (const_int 2)
10706              (const_int 6)))])
10707
10708 ;; In general it is not safe to assume too much about CCmode registers,
10709 ;; so simplify-rtx stops when it sees a second one.  Under certain
10710 ;; conditions this is safe on x86, so help combine not create
10711 ;;
10712 ;;      seta    %al
10713 ;;      testb   %al, %al
10714 ;;      je      Lfoo
10715
10716 (define_split
10717   [(set (pc)
10718         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
10719                                       [(reg FLAGS_REG) (const_int 0)])
10720                           (const_int 0))
10721                       (label_ref (match_operand 1 "" ""))
10722                       (pc)))]
10723   ""
10724   [(set (pc)
10725         (if_then_else (match_dup 0)
10726                       (label_ref (match_dup 1))
10727                       (pc)))]
10728   "PUT_MODE (operands[0], VOIDmode);")
10729
10730 (define_split
10731   [(set (pc)
10732         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
10733                                       [(reg FLAGS_REG) (const_int 0)])
10734                           (const_int 0))
10735                       (label_ref (match_operand 1 "" ""))
10736                       (pc)))]
10737   ""
10738   [(set (pc)
10739         (if_then_else (match_dup 0)
10740                       (label_ref (match_dup 1))
10741                       (pc)))]
10742 {
10743   rtx new_op0 = copy_rtx (operands[0]);
10744   operands[0] = new_op0;
10745   PUT_MODE (new_op0, VOIDmode);
10746   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
10747                                              GET_MODE (XEXP (new_op0, 0))));
10748
10749   /* Make sure that (a) the CCmode we have for the flags is strong
10750      enough for the reversed compare or (b) we have a valid FP compare.  */
10751   if (! ix86_comparison_operator (new_op0, VOIDmode))
10752     FAIL;
10753 })
10754
10755 ;; zero_extend in SImode is correct also for DImode, since this is what combine
10756 ;; pass generates from shift insn with QImode operand.  Actually, the mode
10757 ;; of operand 2 (bit offset operand) doesn't matter since bt insn takes
10758 ;; appropriate modulo of the bit offset value.
10759
10760 (define_insn_and_split "*jcc_bt<mode>"
10761   [(set (pc)
10762         (if_then_else (match_operator 0 "bt_comparison_operator"
10763                         [(zero_extract:SWI48
10764                            (match_operand:SWI48 1 "register_operand" "r")
10765                            (const_int 1)
10766                            (zero_extend:SI
10767                              (match_operand:QI 2 "register_operand" "r")))
10768                          (const_int 0)])
10769                       (label_ref (match_operand 3 "" ""))
10770                       (pc)))
10771    (clobber (reg:CC FLAGS_REG))]
10772   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10773   "#"
10774   "&& 1"
10775   [(set (reg:CCC FLAGS_REG)
10776         (compare:CCC
10777           (zero_extract:SWI48
10778             (match_dup 1)
10779             (const_int 1)
10780             (match_dup 2))
10781           (const_int 0)))
10782    (set (pc)
10783         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10784                       (label_ref (match_dup 3))
10785                       (pc)))]
10786 {
10787   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], QImode, 0);
10788
10789   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10790 })
10791
10792 ;; Avoid useless masking of bit offset operand.  "and" in SImode is correct
10793 ;; also for DImode, this is what combine produces.
10794 (define_insn_and_split "*jcc_bt<mode>_mask"
10795   [(set (pc)
10796         (if_then_else (match_operator 0 "bt_comparison_operator"
10797                         [(zero_extract:SWI48
10798                            (match_operand:SWI48 1 "register_operand" "r")
10799                            (const_int 1)
10800                            (and:SI
10801                              (match_operand:SI 2 "register_operand" "r")
10802                              (match_operand:SI 3 "const_int_operand" "n")))])
10803                       (label_ref (match_operand 4 "" ""))
10804                       (pc)))
10805    (clobber (reg:CC FLAGS_REG))]
10806   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10807    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10808       == GET_MODE_BITSIZE (<MODE>mode)-1"
10809   "#"
10810   "&& 1"
10811   [(set (reg:CCC FLAGS_REG)
10812         (compare:CCC
10813           (zero_extract:SWI48
10814             (match_dup 1)
10815             (const_int 1)
10816             (match_dup 2))
10817           (const_int 0)))
10818    (set (pc)
10819         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10820                       (label_ref (match_dup 4))
10821                       (pc)))]
10822 {
10823   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], SImode, 0);
10824
10825   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10826 })
10827
10828 (define_insn_and_split "*jcc_btsi_1"
10829   [(set (pc)
10830         (if_then_else (match_operator 0 "bt_comparison_operator"
10831                         [(and:SI
10832                            (lshiftrt:SI
10833                              (match_operand:SI 1 "register_operand" "r")
10834                              (match_operand:QI 2 "register_operand" "r"))
10835                            (const_int 1))
10836                          (const_int 0)])
10837                       (label_ref (match_operand 3 "" ""))
10838                       (pc)))
10839    (clobber (reg:CC FLAGS_REG))]
10840   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10841   "#"
10842   "&& 1"
10843   [(set (reg:CCC FLAGS_REG)
10844         (compare:CCC
10845           (zero_extract:SI
10846             (match_dup 1)
10847             (const_int 1)
10848             (match_dup 2))
10849           (const_int 0)))
10850    (set (pc)
10851         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10852                       (label_ref (match_dup 3))
10853                       (pc)))]
10854 {
10855   operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
10856
10857   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10858 })
10859
10860 ;; avoid useless masking of bit offset operand
10861 (define_insn_and_split "*jcc_btsi_mask_1"
10862   [(set (pc)
10863         (if_then_else
10864           (match_operator 0 "bt_comparison_operator"
10865             [(and:SI
10866                (lshiftrt:SI
10867                  (match_operand:SI 1 "register_operand" "r")
10868                  (subreg:QI
10869                    (and:SI
10870                      (match_operand:SI 2 "register_operand" "r")
10871                      (match_operand:SI 3 "const_int_operand" "n")) 0))
10872                (const_int 1))
10873              (const_int 0)])
10874           (label_ref (match_operand 4 "" ""))
10875           (pc)))
10876    (clobber (reg:CC FLAGS_REG))]
10877   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10878    && (INTVAL (operands[3]) & 0x1f) == 0x1f"
10879   "#"
10880   "&& 1"
10881   [(set (reg:CCC FLAGS_REG)
10882         (compare:CCC
10883           (zero_extract:SI
10884             (match_dup 1)
10885             (const_int 1)
10886             (match_dup 2))
10887           (const_int 0)))
10888    (set (pc)
10889         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10890                       (label_ref (match_dup 4))
10891                       (pc)))]
10892   "PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));")
10893
10894 ;; Define combination compare-and-branch fp compare instructions to help
10895 ;; combine.
10896
10897 (define_insn "*fp_jcc_1_387"
10898   [(set (pc)
10899         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10900                         [(match_operand 1 "register_operand" "f")
10901                          (match_operand 2 "nonimmediate_operand" "fm")])
10902           (label_ref (match_operand 3 "" ""))
10903           (pc)))
10904    (clobber (reg:CCFP FPSR_REG))
10905    (clobber (reg:CCFP FLAGS_REG))
10906    (clobber (match_scratch:HI 4 "=a"))]
10907   "TARGET_80387
10908    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10909    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10910    && SELECT_CC_MODE (GET_CODE (operands[0]),
10911                       operands[1], operands[2]) == CCFPmode
10912    && !TARGET_CMOVE"
10913   "#")
10914
10915 (define_insn "*fp_jcc_1r_387"
10916   [(set (pc)
10917         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10918                         [(match_operand 1 "register_operand" "f")
10919                          (match_operand 2 "nonimmediate_operand" "fm")])
10920           (pc)
10921           (label_ref (match_operand 3 "" ""))))
10922    (clobber (reg:CCFP FPSR_REG))
10923    (clobber (reg:CCFP FLAGS_REG))
10924    (clobber (match_scratch:HI 4 "=a"))]
10925   "TARGET_80387
10926    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10927    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10928    && SELECT_CC_MODE (GET_CODE (operands[0]),
10929                       operands[1], operands[2]) == CCFPmode
10930    && !TARGET_CMOVE"
10931   "#")
10932
10933 (define_insn "*fp_jcc_2_387"
10934   [(set (pc)
10935         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10936                         [(match_operand 1 "register_operand" "f")
10937                          (match_operand 2 "register_operand" "f")])
10938           (label_ref (match_operand 3 "" ""))
10939           (pc)))
10940    (clobber (reg:CCFP FPSR_REG))
10941    (clobber (reg:CCFP FLAGS_REG))
10942    (clobber (match_scratch:HI 4 "=a"))]
10943   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10944    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10945    && !TARGET_CMOVE"
10946   "#")
10947
10948 (define_insn "*fp_jcc_2r_387"
10949   [(set (pc)
10950         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10951                         [(match_operand 1 "register_operand" "f")
10952                          (match_operand 2 "register_operand" "f")])
10953           (pc)
10954           (label_ref (match_operand 3 "" ""))))
10955    (clobber (reg:CCFP FPSR_REG))
10956    (clobber (reg:CCFP FLAGS_REG))
10957    (clobber (match_scratch:HI 4 "=a"))]
10958   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10959    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10960    && !TARGET_CMOVE"
10961   "#")
10962
10963 (define_insn "*fp_jcc_3_387"
10964   [(set (pc)
10965         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10966                         [(match_operand 1 "register_operand" "f")
10967                          (match_operand 2 "const0_operand" "")])
10968           (label_ref (match_operand 3 "" ""))
10969           (pc)))
10970    (clobber (reg:CCFP FPSR_REG))
10971    (clobber (reg:CCFP FLAGS_REG))
10972    (clobber (match_scratch:HI 4 "=a"))]
10973   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10974    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10975    && SELECT_CC_MODE (GET_CODE (operands[0]),
10976                       operands[1], operands[2]) == CCFPmode
10977    && !TARGET_CMOVE"
10978   "#")
10979
10980 (define_split
10981   [(set (pc)
10982         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10983                         [(match_operand 1 "register_operand" "")
10984                          (match_operand 2 "nonimmediate_operand" "")])
10985           (match_operand 3 "" "")
10986           (match_operand 4 "" "")))
10987    (clobber (reg:CCFP FPSR_REG))
10988    (clobber (reg:CCFP FLAGS_REG))]
10989   "reload_completed"
10990   [(const_int 0)]
10991 {
10992   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
10993                         operands[3], operands[4], NULL_RTX, NULL_RTX);
10994   DONE;
10995 })
10996
10997 (define_split
10998   [(set (pc)
10999         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
11000                         [(match_operand 1 "register_operand" "")
11001                          (match_operand 2 "general_operand" "")])
11002           (match_operand 3 "" "")
11003           (match_operand 4 "" "")))
11004    (clobber (reg:CCFP FPSR_REG))
11005    (clobber (reg:CCFP FLAGS_REG))
11006    (clobber (match_scratch:HI 5 "=a"))]
11007   "reload_completed"
11008   [(const_int 0)]
11009 {
11010   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
11011                         operands[3], operands[4], operands[5], NULL_RTX);
11012   DONE;
11013 })
11014
11015 ;; The order of operands in *fp_jcc_4_387 is forced by combine in
11016 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
11017 ;; with a precedence over other operators and is always put in the first
11018 ;; place. Swap condition and operands to match ficom instruction.
11019
11020 (define_insn "*fp_jcc_4_<mode>_387"
11021   [(set (pc)
11022         (if_then_else
11023           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11024             [(match_operator 1 "float_operator"
11025               [(match_operand:SWI24 2 "nonimmediate_operand" "m,?r")])
11026              (match_operand 3 "register_operand" "f,f")])
11027           (label_ref (match_operand 4 "" ""))
11028           (pc)))
11029    (clobber (reg:CCFP FPSR_REG))
11030    (clobber (reg:CCFP FLAGS_REG))
11031    (clobber (match_scratch:HI 5 "=a,a"))]
11032   "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
11033    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
11034    && GET_MODE (operands[1]) == GET_MODE (operands[3])
11035    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
11036    && !TARGET_CMOVE"
11037   "#")
11038
11039 (define_split
11040   [(set (pc)
11041         (if_then_else
11042           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11043             [(match_operator 1 "float_operator"
11044               [(match_operand:SWI24 2 "memory_operand" "")])
11045              (match_operand 3 "register_operand" "")])
11046           (match_operand 4 "" "")
11047           (match_operand 5 "" "")))
11048    (clobber (reg:CCFP FPSR_REG))
11049    (clobber (reg:CCFP FLAGS_REG))
11050    (clobber (match_scratch:HI 6 "=a"))]
11051   "reload_completed"
11052   [(const_int 0)]
11053 {
11054   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
11055
11056   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11057                         operands[3], operands[7],
11058                         operands[4], operands[5], operands[6], NULL_RTX);
11059   DONE;
11060 })
11061
11062 ;; %%% Kill this when reload knows how to do it.
11063 (define_split
11064   [(set (pc)
11065         (if_then_else
11066           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11067             [(match_operator 1 "float_operator"
11068               [(match_operand:SWI24 2 "register_operand" "")])
11069              (match_operand 3 "register_operand" "")])
11070           (match_operand 4 "" "")
11071           (match_operand 5 "" "")))
11072    (clobber (reg:CCFP FPSR_REG))
11073    (clobber (reg:CCFP FLAGS_REG))
11074    (clobber (match_scratch:HI 6 "=a"))]
11075   "reload_completed"
11076   [(const_int 0)]
11077 {
11078   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
11079   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
11080
11081   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11082                         operands[3], operands[7],
11083                         operands[4], operands[5], operands[6], operands[2]);
11084   DONE;
11085 })
11086 \f
11087 ;; Unconditional and other jump instructions
11088
11089 (define_insn "jump"
11090   [(set (pc)
11091         (label_ref (match_operand 0 "" "")))]
11092   ""
11093   "jmp\t%l0"
11094   [(set_attr "type" "ibr")
11095    (set (attr "length")
11096            (if_then_else (and (ge (minus (match_dup 0) (pc))
11097                                   (const_int -126))
11098                               (lt (minus (match_dup 0) (pc))
11099                                   (const_int 128)))
11100              (const_int 2)
11101              (const_int 5)))
11102    (set_attr "modrm" "0")])
11103
11104 (define_expand "indirect_jump"
11105   [(set (pc) (match_operand 0 "indirect_branch_operand" ""))])
11106
11107 (define_insn "*indirect_jump"
11108   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))]
11109   ""
11110   "jmp\t%A0"
11111   [(set_attr "type" "ibr")
11112    (set_attr "length_immediate" "0")])
11113
11114 (define_expand "tablejump"
11115   [(parallel [(set (pc) (match_operand 0 "indirect_branch_operand" ""))
11116               (use (label_ref (match_operand 1 "" "")))])]
11117   ""
11118 {
11119   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
11120      relative.  Convert the relative address to an absolute address.  */
11121   if (flag_pic)
11122     {
11123       rtx op0, op1;
11124       enum rtx_code code;
11125
11126       /* We can't use @GOTOFF for text labels on VxWorks;
11127          see gotoff_operand.  */
11128       if (TARGET_64BIT || TARGET_VXWORKS_RTP)
11129         {
11130           code = PLUS;
11131           op0 = operands[0];
11132           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
11133         }
11134       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
11135         {
11136           code = PLUS;
11137           op0 = operands[0];
11138           op1 = pic_offset_table_rtx;
11139         }
11140       else
11141         {
11142           code = MINUS;
11143           op0 = pic_offset_table_rtx;
11144           op1 = operands[0];
11145         }
11146
11147       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
11148                                          OPTAB_DIRECT);
11149     }
11150   else if (TARGET_X32)
11151     operands[0] = convert_memory_address (Pmode, operands[0]);
11152 })
11153
11154 (define_insn "*tablejump_1"
11155   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))
11156    (use (label_ref (match_operand 1 "" "")))]
11157   ""
11158   "jmp\t%A0"
11159   [(set_attr "type" "ibr")
11160    (set_attr "length_immediate" "0")])
11161 \f
11162 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
11163
11164 (define_peephole2
11165   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11166    (set (match_operand:QI 1 "register_operand" "")
11167         (match_operator:QI 2 "ix86_comparison_operator"
11168           [(reg FLAGS_REG) (const_int 0)]))
11169    (set (match_operand 3 "q_regs_operand" "")
11170         (zero_extend (match_dup 1)))]
11171   "(peep2_reg_dead_p (3, operands[1])
11172     || operands_match_p (operands[1], operands[3]))
11173    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11174   [(set (match_dup 4) (match_dup 0))
11175    (set (strict_low_part (match_dup 5))
11176         (match_dup 2))]
11177 {
11178   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11179   operands[5] = gen_lowpart (QImode, operands[3]);
11180   ix86_expand_clear (operands[3]);
11181 })
11182
11183 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
11184
11185 (define_peephole2
11186   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11187    (set (match_operand:QI 1 "register_operand" "")
11188         (match_operator:QI 2 "ix86_comparison_operator"
11189           [(reg FLAGS_REG) (const_int 0)]))
11190    (parallel [(set (match_operand 3 "q_regs_operand" "")
11191                    (zero_extend (match_dup 1)))
11192               (clobber (reg:CC FLAGS_REG))])]
11193   "(peep2_reg_dead_p (3, operands[1])
11194     || operands_match_p (operands[1], operands[3]))
11195    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11196   [(set (match_dup 4) (match_dup 0))
11197    (set (strict_low_part (match_dup 5))
11198         (match_dup 2))]
11199 {
11200   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11201   operands[5] = gen_lowpart (QImode, operands[3]);
11202   ix86_expand_clear (operands[3]);
11203 })
11204 \f
11205 ;; Call instructions.
11206
11207 ;; The predicates normally associated with named expanders are not properly
11208 ;; checked for calls.  This is a bug in the generic code, but it isn't that
11209 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
11210
11211 ;; P6 processors will jump to the address after the decrement when %esp
11212 ;; is used as a call operand, so they will execute return address as a code.
11213 ;; See Pentium Pro errata 70, Pentium 2 errata A33 and Pentium 3 errata E17.
11214
11215 ;; Register constraint for call instruction.
11216 (define_mode_attr c [(SI "l") (DI "r")])
11217
11218 ;; Call subroutine returning no value.
11219
11220 (define_expand "call"
11221   [(call (match_operand:QI 0 "" "")
11222          (match_operand 1 "" ""))
11223    (use (match_operand 2 "" ""))]
11224   ""
11225 {
11226   ix86_expand_call (NULL, operands[0], operands[1],
11227                     operands[2], NULL, false);
11228   DONE;
11229 })
11230
11231 (define_expand "sibcall"
11232   [(call (match_operand:QI 0 "" "")
11233          (match_operand 1 "" ""))
11234    (use (match_operand 2 "" ""))]
11235   ""
11236 {
11237   ix86_expand_call (NULL, operands[0], operands[1],
11238                     operands[2], NULL, true);
11239   DONE;
11240 })
11241
11242 (define_insn_and_split "*call_vzeroupper"
11243   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11244          (match_operand 1 "" ""))
11245    (unspec [(match_operand 2 "const_int_operand" "")]
11246            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11247   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11248   "#"
11249   "&& reload_completed"
11250   [(const_int 0)]
11251   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11252   [(set_attr "type" "call")])
11253
11254 (define_insn "*call"
11255   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11256          (match_operand 1 "" ""))]
11257   "!SIBLING_CALL_P (insn)"
11258   "* return ix86_output_call_insn (insn, operands[0]);"
11259   [(set_attr "type" "call")])
11260
11261 (define_insn_and_split "*call_rex64_ms_sysv_vzeroupper"
11262   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11263          (match_operand 1 "" ""))
11264    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11265    (clobber (reg:TI XMM6_REG))
11266    (clobber (reg:TI XMM7_REG))
11267    (clobber (reg:TI XMM8_REG))
11268    (clobber (reg:TI XMM9_REG))
11269    (clobber (reg:TI XMM10_REG))
11270    (clobber (reg:TI XMM11_REG))
11271    (clobber (reg:TI XMM12_REG))
11272    (clobber (reg:TI XMM13_REG))
11273    (clobber (reg:TI XMM14_REG))
11274    (clobber (reg:TI XMM15_REG))
11275    (clobber (reg:DI SI_REG))
11276    (clobber (reg:DI DI_REG))
11277    (unspec [(match_operand 2 "const_int_operand" "")]
11278            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11279   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11280   "#"
11281   "&& reload_completed"
11282   [(const_int 0)]
11283   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11284   [(set_attr "type" "call")])
11285
11286 (define_insn "*call_rex64_ms_sysv"
11287   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11288          (match_operand 1 "" ""))
11289    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11290    (clobber (reg:TI XMM6_REG))
11291    (clobber (reg:TI XMM7_REG))
11292    (clobber (reg:TI XMM8_REG))
11293    (clobber (reg:TI XMM9_REG))
11294    (clobber (reg:TI XMM10_REG))
11295    (clobber (reg:TI XMM11_REG))
11296    (clobber (reg:TI XMM12_REG))
11297    (clobber (reg:TI XMM13_REG))
11298    (clobber (reg:TI XMM14_REG))
11299    (clobber (reg:TI XMM15_REG))
11300    (clobber (reg:DI SI_REG))
11301    (clobber (reg:DI DI_REG))]
11302   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11303   "* return ix86_output_call_insn (insn, operands[0]);"
11304   [(set_attr "type" "call")])
11305
11306 (define_insn_and_split "*sibcall_vzeroupper"
11307   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11308          (match_operand 1 "" ""))
11309    (unspec [(match_operand 2 "const_int_operand" "")]
11310            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11311   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11312   "#"
11313   "&& reload_completed"
11314   [(const_int 0)]
11315   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11316   [(set_attr "type" "call")])
11317
11318 (define_insn "*sibcall"
11319   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11320          (match_operand 1 "" ""))]
11321   "SIBLING_CALL_P (insn)"
11322   "* return ix86_output_call_insn (insn, operands[0]);"
11323   [(set_attr "type" "call")])
11324
11325 (define_expand "call_pop"
11326   [(parallel [(call (match_operand:QI 0 "" "")
11327                     (match_operand:SI 1 "" ""))
11328               (set (reg:SI SP_REG)
11329                    (plus:SI (reg:SI SP_REG)
11330                             (match_operand:SI 3 "" "")))])]
11331   "!TARGET_64BIT"
11332 {
11333   ix86_expand_call (NULL, operands[0], operands[1],
11334                     operands[2], operands[3], false);
11335   DONE;
11336 })
11337
11338 (define_insn_and_split "*call_pop_vzeroupper"
11339   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11340          (match_operand:SI 1 "" ""))
11341    (set (reg:SI SP_REG)
11342         (plus:SI (reg:SI SP_REG)
11343                  (match_operand:SI 2 "immediate_operand" "i")))
11344    (unspec [(match_operand 3 "const_int_operand" "")]
11345            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11346   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11347   "#"
11348   "&& reload_completed"
11349   [(const_int 0)]
11350   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11351   [(set_attr "type" "call")])
11352
11353 (define_insn "*call_pop"
11354   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11355          (match_operand 1 "" ""))
11356    (set (reg:SI SP_REG)
11357         (plus:SI (reg:SI SP_REG)
11358                  (match_operand:SI 2 "immediate_operand" "i")))]
11359   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11360   "* return ix86_output_call_insn (insn, operands[0]);"
11361   [(set_attr "type" "call")])
11362
11363 (define_insn_and_split "*sibcall_pop_vzeroupper"
11364   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11365          (match_operand 1 "" ""))
11366    (set (reg:SI SP_REG)
11367         (plus:SI (reg:SI SP_REG)
11368                  (match_operand:SI 2 "immediate_operand" "i")))
11369    (unspec [(match_operand 3 "const_int_operand" "")]
11370            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11371   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11372   "#"
11373   "&& reload_completed"
11374   [(const_int 0)]
11375   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11376   [(set_attr "type" "call")])
11377
11378 (define_insn "*sibcall_pop"
11379   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11380          (match_operand 1 "" ""))
11381    (set (reg:SI SP_REG)
11382         (plus:SI (reg:SI SP_REG)
11383                  (match_operand:SI 2 "immediate_operand" "i")))]
11384   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11385   "* return ix86_output_call_insn (insn, operands[0]);"
11386   [(set_attr "type" "call")])
11387
11388 ;; Call subroutine, returning value in operand 0
11389
11390 (define_expand "call_value"
11391   [(set (match_operand 0 "" "")
11392         (call (match_operand:QI 1 "" "")
11393               (match_operand 2 "" "")))
11394    (use (match_operand 3 "" ""))]
11395   ""
11396 {
11397   ix86_expand_call (operands[0], operands[1], operands[2],
11398                     operands[3], NULL, false);
11399   DONE;
11400 })
11401
11402 (define_expand "sibcall_value"
11403   [(set (match_operand 0 "" "")
11404         (call (match_operand:QI 1 "" "")
11405               (match_operand 2 "" "")))
11406    (use (match_operand 3 "" ""))]
11407   ""
11408 {
11409   ix86_expand_call (operands[0], operands[1], operands[2],
11410                     operands[3], NULL, true);
11411   DONE;
11412 })
11413
11414 (define_insn_and_split "*call_value_vzeroupper"
11415   [(set (match_operand 0 "" "")
11416         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11417               (match_operand 2 "" "")))
11418    (unspec [(match_operand 3 "const_int_operand" "")]
11419            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11420   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11421   "#"
11422   "&& reload_completed"
11423   [(const_int 0)]
11424   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11425   [(set_attr "type" "callv")])
11426
11427 (define_insn "*call_value"
11428   [(set (match_operand 0 "" "")
11429         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11430               (match_operand 2 "" "")))]
11431   "!SIBLING_CALL_P (insn)"
11432   "* return ix86_output_call_insn (insn, operands[1]);"
11433   [(set_attr "type" "callv")])
11434
11435 (define_insn_and_split "*sibcall_value_vzeroupper"
11436   [(set (match_operand 0 "" "")
11437         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11438               (match_operand 2 "" "")))
11439    (unspec [(match_operand 3 "const_int_operand" "")]
11440            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11441   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11442   "#"
11443   "&& reload_completed"
11444   [(const_int 0)]
11445   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11446   [(set_attr "type" "callv")])
11447
11448 (define_insn "*sibcall_value"
11449   [(set (match_operand 0 "" "")
11450         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11451               (match_operand 2 "" "")))]
11452   "SIBLING_CALL_P (insn)"
11453   "* return ix86_output_call_insn (insn, operands[1]);"
11454   [(set_attr "type" "callv")])
11455
11456 (define_insn_and_split "*call_value_rex64_ms_sysv_vzeroupper"
11457   [(set (match_operand 0 "" "")
11458         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11459               (match_operand 2 "" "")))
11460    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11461    (clobber (reg:TI XMM6_REG))
11462    (clobber (reg:TI XMM7_REG))
11463    (clobber (reg:TI XMM8_REG))
11464    (clobber (reg:TI XMM9_REG))
11465    (clobber (reg:TI XMM10_REG))
11466    (clobber (reg:TI XMM11_REG))
11467    (clobber (reg:TI XMM12_REG))
11468    (clobber (reg:TI XMM13_REG))
11469    (clobber (reg:TI XMM14_REG))
11470    (clobber (reg:TI XMM15_REG))
11471    (clobber (reg:DI SI_REG))
11472    (clobber (reg:DI DI_REG))
11473    (unspec [(match_operand 3 "const_int_operand" "")]
11474            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11475   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11476   "#"
11477   "&& reload_completed"
11478   [(const_int 0)]
11479   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11480   [(set_attr "type" "callv")])
11481
11482 (define_insn "*call_value_rex64_ms_sysv"
11483   [(set (match_operand 0 "" "")
11484         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11485               (match_operand 2 "" "")))
11486    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11487    (clobber (reg:TI XMM6_REG))
11488    (clobber (reg:TI XMM7_REG))
11489    (clobber (reg:TI XMM8_REG))
11490    (clobber (reg:TI XMM9_REG))
11491    (clobber (reg:TI XMM10_REG))
11492    (clobber (reg:TI XMM11_REG))
11493    (clobber (reg:TI XMM12_REG))
11494    (clobber (reg:TI XMM13_REG))
11495    (clobber (reg:TI XMM14_REG))
11496    (clobber (reg:TI XMM15_REG))
11497    (clobber (reg:DI SI_REG))
11498    (clobber (reg:DI DI_REG))]
11499   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11500   "* return ix86_output_call_insn (insn, operands[1]);"
11501   [(set_attr "type" "callv")])
11502
11503 (define_expand "call_value_pop"
11504   [(parallel [(set (match_operand 0 "" "")
11505                    (call (match_operand:QI 1 "" "")
11506                          (match_operand:SI 2 "" "")))
11507               (set (reg:SI SP_REG)
11508                    (plus:SI (reg:SI SP_REG)
11509                             (match_operand:SI 4 "" "")))])]
11510   "!TARGET_64BIT"
11511 {
11512   ix86_expand_call (operands[0], operands[1], operands[2],
11513                     operands[3], operands[4], false);
11514   DONE;
11515 })
11516
11517 (define_insn_and_split "*call_value_pop_vzeroupper"
11518   [(set (match_operand 0 "" "")
11519         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11520               (match_operand 2 "" "")))
11521    (set (reg:SI SP_REG)
11522         (plus:SI (reg:SI SP_REG)
11523                  (match_operand:SI 3 "immediate_operand" "i")))
11524    (unspec [(match_operand 4 "const_int_operand" "")]
11525            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11526   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11527   "#"
11528   "&& reload_completed"
11529   [(const_int 0)]
11530   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11531   [(set_attr "type" "callv")])
11532
11533 (define_insn "*call_value_pop"
11534   [(set (match_operand 0 "" "")
11535         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11536               (match_operand 2 "" "")))
11537    (set (reg:SI SP_REG)
11538         (plus:SI (reg:SI SP_REG)
11539                  (match_operand:SI 3 "immediate_operand" "i")))]
11540   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11541   "* return ix86_output_call_insn (insn, operands[1]);"
11542   [(set_attr "type" "callv")])
11543
11544 (define_insn_and_split "*sibcall_value_pop_vzeroupper"
11545   [(set (match_operand 0 "" "")
11546         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11547               (match_operand 2 "" "")))
11548    (set (reg:SI SP_REG)
11549         (plus:SI (reg:SI SP_REG)
11550                  (match_operand:SI 3 "immediate_operand" "i")))
11551    (unspec [(match_operand 4 "const_int_operand" "")]
11552            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11553   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11554   "#"
11555   "&& reload_completed"
11556   [(const_int 0)]
11557   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11558   [(set_attr "type" "callv")])
11559
11560 (define_insn "*sibcall_value_pop"
11561   [(set (match_operand 0 "" "")
11562         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11563               (match_operand 2 "" "")))
11564    (set (reg:SI SP_REG)
11565         (plus:SI (reg:SI SP_REG)
11566                  (match_operand:SI 3 "immediate_operand" "i")))]
11567   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11568   "* return ix86_output_call_insn (insn, operands[1]);"
11569   [(set_attr "type" "callv")])
11570
11571 ;; Call subroutine returning any type.
11572
11573 (define_expand "untyped_call"
11574   [(parallel [(call (match_operand 0 "" "")
11575                     (const_int 0))
11576               (match_operand 1 "" "")
11577               (match_operand 2 "" "")])]
11578   ""
11579 {
11580   int i;
11581
11582   /* In order to give reg-stack an easier job in validating two
11583      coprocessor registers as containing a possible return value,
11584      simply pretend the untyped call returns a complex long double
11585      value. 
11586
11587      We can't use SSE_REGPARM_MAX here since callee is unprototyped
11588      and should have the default ABI.  */
11589
11590   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
11591                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
11592                     operands[0], const0_rtx,
11593                     GEN_INT ((TARGET_64BIT
11594                               ? (ix86_abi == SYSV_ABI
11595                                  ? X86_64_SSE_REGPARM_MAX
11596                                  : X86_64_MS_SSE_REGPARM_MAX)
11597                               : X86_32_SSE_REGPARM_MAX)
11598                              - 1),
11599                     NULL, false);
11600
11601   for (i = 0; i < XVECLEN (operands[2], 0); i++)
11602     {
11603       rtx set = XVECEXP (operands[2], 0, i);
11604       emit_move_insn (SET_DEST (set), SET_SRC (set));
11605     }
11606
11607   /* The optimizer does not know that the call sets the function value
11608      registers we stored in the result block.  We avoid problems by
11609      claiming that all hard registers are used and clobbered at this
11610      point.  */
11611   emit_insn (gen_blockage ());
11612
11613   DONE;
11614 })
11615 \f
11616 ;; Prologue and epilogue instructions
11617
11618 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
11619 ;; all of memory.  This blocks insns from being moved across this point.
11620
11621 (define_insn "blockage"
11622   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
11623   ""
11624   ""
11625   [(set_attr "length" "0")])
11626
11627 ;; Do not schedule instructions accessing memory across this point.
11628
11629 (define_expand "memory_blockage"
11630   [(set (match_dup 0)
11631         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11632   ""
11633 {
11634   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
11635   MEM_VOLATILE_P (operands[0]) = 1;
11636 })
11637
11638 (define_insn "*memory_blockage"
11639   [(set (match_operand:BLK 0 "" "")
11640         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11641   ""
11642   ""
11643   [(set_attr "length" "0")])
11644
11645 ;; As USE insns aren't meaningful after reload, this is used instead
11646 ;; to prevent deleting instructions setting registers for PIC code
11647 (define_insn "prologue_use"
11648   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
11649   ""
11650   ""
11651   [(set_attr "length" "0")])
11652
11653 ;; Insn emitted into the body of a function to return from a function.
11654 ;; This is only done if the function's epilogue is known to be simple.
11655 ;; See comments for ix86_can_use_return_insn_p in i386.c.
11656
11657 (define_expand "return"
11658   [(simple_return)]
11659   "ix86_can_use_return_insn_p ()"
11660 {
11661   ix86_maybe_emit_epilogue_vzeroupper ();
11662   if (crtl->args.pops_args)
11663     {
11664       rtx popc = GEN_INT (crtl->args.pops_args);
11665       emit_jump_insn (gen_simple_return_pop_internal (popc));
11666       DONE;
11667     }
11668 })
11669
11670 ;; We need to disable this for TARGET_SEH, as otherwise
11671 ;; shrink-wrapped prologue gets enabled too.  This might exceed
11672 ;; the maximum size of prologue in unwind information.
11673
11674 (define_expand "simple_return"
11675   [(simple_return)]
11676   "!TARGET_SEH"
11677 {
11678   ix86_maybe_emit_epilogue_vzeroupper ();
11679   if (crtl->args.pops_args)
11680     {
11681       rtx popc = GEN_INT (crtl->args.pops_args);
11682       emit_jump_insn (gen_simple_return_pop_internal (popc));
11683       DONE;
11684     }
11685 })
11686
11687 (define_insn "simple_return_internal"
11688   [(simple_return)]
11689   "reload_completed"
11690   "ret"
11691   [(set_attr "length" "1")
11692    (set_attr "atom_unit" "jeu")
11693    (set_attr "length_immediate" "0")
11694    (set_attr "modrm" "0")])
11695
11696 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
11697 ;; instruction Athlon and K8 have.
11698
11699 (define_insn "simple_return_internal_long"
11700   [(simple_return)
11701    (unspec [(const_int 0)] UNSPEC_REP)]
11702   "reload_completed"
11703   "rep\;ret"
11704   [(set_attr "length" "2")
11705    (set_attr "atom_unit" "jeu")
11706    (set_attr "length_immediate" "0")
11707    (set_attr "prefix_rep" "1")
11708    (set_attr "modrm" "0")])
11709
11710 (define_insn "simple_return_pop_internal"
11711   [(simple_return)
11712    (use (match_operand:SI 0 "const_int_operand" ""))]
11713   "reload_completed"
11714   "ret\t%0"
11715   [(set_attr "length" "3")
11716    (set_attr "atom_unit" "jeu")
11717    (set_attr "length_immediate" "2")
11718    (set_attr "modrm" "0")])
11719
11720 (define_insn "simple_return_indirect_internal"
11721   [(simple_return)
11722    (use (match_operand:SI 0 "register_operand" "r"))]
11723   "reload_completed"
11724   "jmp\t%A0"
11725   [(set_attr "type" "ibr")
11726    (set_attr "length_immediate" "0")])
11727
11728 (define_insn "nop"
11729   [(const_int 0)]
11730   ""
11731   "nop"
11732   [(set_attr "length" "1")
11733    (set_attr "length_immediate" "0")
11734    (set_attr "modrm" "0")])
11735
11736 ;; Generate nops.  Operand 0 is the number of nops, up to 8.
11737 (define_insn "nops"
11738   [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
11739                     UNSPECV_NOPS)]
11740   "reload_completed"
11741 {
11742   int num = INTVAL (operands[0]);
11743
11744   gcc_assert (num >= 1 && num <= 8);
11745
11746   while (num--)
11747     fputs ("\tnop\n", asm_out_file);
11748
11749   return "";
11750 }
11751   [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))
11752    (set_attr "length_immediate" "0")
11753    (set_attr "modrm" "0")])
11754
11755 ;; Pad to 16-byte boundary, max skip in op0.  Used to avoid
11756 ;; branch prediction penalty for the third jump in a 16-byte
11757 ;; block on K8.
11758
11759 (define_insn "pad"
11760   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
11761   ""
11762 {
11763 #ifdef ASM_OUTPUT_MAX_SKIP_PAD
11764   ASM_OUTPUT_MAX_SKIP_PAD (asm_out_file, 4, (int)INTVAL (operands[0]));
11765 #else
11766   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
11767      The align insn is used to avoid 3 jump instructions in the row to improve
11768      branch prediction and the benefits hardly outweigh the cost of extra 8
11769      nops on the average inserted by full alignment pseudo operation.  */
11770 #endif
11771   return "";
11772 }
11773   [(set_attr "length" "16")])
11774
11775 (define_expand "prologue"
11776   [(const_int 0)]
11777   ""
11778   "ix86_expand_prologue (); DONE;")
11779
11780 (define_insn "set_got"
11781   [(set (match_operand:SI 0 "register_operand" "=r")
11782         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
11783    (clobber (reg:CC FLAGS_REG))]
11784   "!TARGET_64BIT"
11785   "* return output_set_got (operands[0], NULL_RTX);"
11786   [(set_attr "type" "multi")
11787    (set_attr "length" "12")])
11788
11789 (define_insn "set_got_labelled"
11790   [(set (match_operand:SI 0 "register_operand" "=r")
11791         (unspec:SI [(label_ref (match_operand 1 "" ""))]
11792          UNSPEC_SET_GOT))
11793    (clobber (reg:CC FLAGS_REG))]
11794   "!TARGET_64BIT"
11795   "* return output_set_got (operands[0], operands[1]);"
11796   [(set_attr "type" "multi")
11797    (set_attr "length" "12")])
11798
11799 (define_insn "set_got_rex64"
11800   [(set (match_operand:DI 0 "register_operand" "=r")
11801         (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
11802   "TARGET_64BIT"
11803   "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
11804   [(set_attr "type" "lea")
11805    (set_attr "length_address" "4")
11806    (set_attr "mode" "DI")])
11807
11808 (define_insn "set_rip_rex64"
11809   [(set (match_operand:DI 0 "register_operand" "=r")
11810         (unspec:DI [(label_ref (match_operand 1 "" ""))] UNSPEC_SET_RIP))]
11811   "TARGET_64BIT"
11812   "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
11813   [(set_attr "type" "lea")
11814    (set_attr "length_address" "4")
11815    (set_attr "mode" "DI")])
11816
11817 (define_insn "set_got_offset_rex64"
11818   [(set (match_operand:DI 0 "register_operand" "=r")
11819         (unspec:DI
11820           [(label_ref (match_operand 1 "" ""))]
11821           UNSPEC_SET_GOT_OFFSET))]
11822   "TARGET_LP64"
11823   "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
11824   [(set_attr "type" "imov")
11825    (set_attr "length_immediate" "0")
11826    (set_attr "length_address" "8")
11827    (set_attr "mode" "DI")])
11828
11829 (define_expand "epilogue"
11830   [(const_int 0)]
11831   ""
11832   "ix86_expand_epilogue (1); DONE;")
11833
11834 (define_expand "sibcall_epilogue"
11835   [(const_int 0)]
11836   ""
11837   "ix86_expand_epilogue (0); DONE;")
11838
11839 (define_expand "eh_return"
11840   [(use (match_operand 0 "register_operand" ""))]
11841   ""
11842 {
11843   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
11844
11845   /* Tricky bit: we write the address of the handler to which we will
11846      be returning into someone else's stack frame, one word below the
11847      stack address we wish to restore.  */
11848   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
11849   tmp = plus_constant (tmp, -UNITS_PER_WORD);
11850   tmp = gen_rtx_MEM (Pmode, tmp);
11851   emit_move_insn (tmp, ra);
11852
11853   emit_jump_insn (gen_eh_return_internal ());
11854   emit_barrier ();
11855   DONE;
11856 })
11857
11858 (define_insn_and_split "eh_return_internal"
11859   [(eh_return)]
11860   ""
11861   "#"
11862   "epilogue_completed"
11863   [(const_int 0)]
11864   "ix86_expand_epilogue (2); DONE;")
11865
11866 (define_insn "leave"
11867   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
11868    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
11869    (clobber (mem:BLK (scratch)))]
11870   "!TARGET_64BIT"
11871   "leave"
11872   [(set_attr "type" "leave")])
11873
11874 (define_insn "leave_rex64"
11875   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
11876    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
11877    (clobber (mem:BLK (scratch)))]
11878   "TARGET_64BIT"
11879   "leave"
11880   [(set_attr "type" "leave")])
11881 \f
11882 ;; Handle -fsplit-stack.
11883
11884 (define_expand "split_stack_prologue"
11885   [(const_int 0)]
11886   ""
11887 {
11888   ix86_expand_split_stack_prologue ();
11889   DONE;
11890 })
11891
11892 ;; In order to support the call/return predictor, we use a return
11893 ;; instruction which the middle-end doesn't see.
11894 (define_insn "split_stack_return"
11895   [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "")]
11896                      UNSPECV_SPLIT_STACK_RETURN)]
11897   ""
11898 {
11899   if (operands[0] == const0_rtx)
11900     return "ret";
11901   else
11902     return "ret\t%0";
11903 }
11904   [(set_attr "atom_unit" "jeu")
11905    (set_attr "modrm" "0")
11906    (set (attr "length")
11907         (if_then_else (match_operand:SI 0 "const0_operand" "")
11908                       (const_int 1)
11909                       (const_int 3)))
11910    (set (attr "length_immediate")
11911         (if_then_else (match_operand:SI 0 "const0_operand" "")
11912                       (const_int 0)
11913                       (const_int 2)))])
11914
11915 ;; If there are operand 0 bytes available on the stack, jump to
11916 ;; operand 1.
11917
11918 (define_expand "split_stack_space_check"
11919   [(set (pc) (if_then_else
11920               (ltu (minus (reg SP_REG)
11921                           (match_operand 0 "register_operand" ""))
11922                    (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
11923               (label_ref (match_operand 1 "" ""))
11924               (pc)))]
11925   ""
11926 {
11927   rtx reg, size, limit;
11928
11929   reg = gen_reg_rtx (Pmode);
11930   size = force_reg (Pmode, operands[0]);
11931   emit_insn (gen_sub3_insn (reg, stack_pointer_rtx, size));
11932   limit = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx),
11933                           UNSPEC_STACK_CHECK);
11934   limit = gen_rtx_MEM (Pmode, gen_rtx_CONST (Pmode, limit));
11935   ix86_expand_branch (GEU, reg, limit, operands[1]);
11936
11937   DONE;
11938 })
11939 \f
11940 ;; Bit manipulation instructions.
11941
11942 (define_expand "ffs<mode>2"
11943   [(set (match_dup 2) (const_int -1))
11944    (parallel [(set (reg:CCZ FLAGS_REG)
11945                    (compare:CCZ
11946                      (match_operand:SWI48 1 "nonimmediate_operand" "")
11947                      (const_int 0)))
11948               (set (match_operand:SWI48 0 "register_operand" "")
11949                    (ctz:SWI48 (match_dup 1)))])
11950    (set (match_dup 0) (if_then_else:SWI48
11951                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
11952                         (match_dup 2)
11953                         (match_dup 0)))
11954    (parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (const_int 1)))
11955               (clobber (reg:CC FLAGS_REG))])]
11956   ""
11957 {
11958   if (<MODE>mode == SImode && !TARGET_CMOVE)
11959     {
11960       emit_insn (gen_ffssi2_no_cmove (operands[0], operands [1]));
11961       DONE;
11962     }
11963   operands[2] = gen_reg_rtx (<MODE>mode);
11964 })
11965
11966 (define_insn_and_split "ffssi2_no_cmove"
11967   [(set (match_operand:SI 0 "register_operand" "=r")
11968         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
11969    (clobber (match_scratch:SI 2 "=&q"))
11970    (clobber (reg:CC FLAGS_REG))]
11971   "!TARGET_CMOVE"
11972   "#"
11973   "&& reload_completed"
11974   [(parallel [(set (reg:CCZ FLAGS_REG)
11975                    (compare:CCZ (match_dup 1) (const_int 0)))
11976               (set (match_dup 0) (ctz:SI (match_dup 1)))])
11977    (set (strict_low_part (match_dup 3))
11978         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
11979    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
11980               (clobber (reg:CC FLAGS_REG))])
11981    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
11982               (clobber (reg:CC FLAGS_REG))])
11983    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
11984               (clobber (reg:CC FLAGS_REG))])]
11985 {
11986   operands[3] = gen_lowpart (QImode, operands[2]);
11987   ix86_expand_clear (operands[2]);
11988 })
11989
11990 (define_insn "*ffs<mode>_1"
11991   [(set (reg:CCZ FLAGS_REG)
11992         (compare:CCZ (match_operand:SWI48 1 "nonimmediate_operand" "rm")
11993                      (const_int 0)))
11994    (set (match_operand:SWI48 0 "register_operand" "=r")
11995         (ctz:SWI48 (match_dup 1)))]
11996   ""
11997   "bsf{<imodesuffix>}\t{%1, %0|%0, %1}"
11998   [(set_attr "type" "alu1")
11999    (set_attr "prefix_0f" "1")
12000    (set_attr "mode" "<MODE>")])
12001
12002 (define_insn "ctz<mode>2"
12003   [(set (match_operand:SWI248 0 "register_operand" "=r")
12004         (ctz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12005    (clobber (reg:CC FLAGS_REG))]
12006   ""
12007 {
12008   if (TARGET_BMI)
12009     return "tzcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12010   else
12011     return "bsf{<imodesuffix>}\t{%1, %0|%0, %1}";
12012 }
12013   [(set_attr "type" "alu1")
12014    (set_attr "prefix_0f" "1")
12015    (set (attr "prefix_rep") (symbol_ref "TARGET_BMI"))
12016    (set_attr "mode" "<MODE>")])
12017
12018 (define_expand "clz<mode>2"
12019   [(parallel
12020      [(set (match_operand:SWI248 0 "register_operand" "")
12021            (minus:SWI248
12022              (match_dup 2)
12023              (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" ""))))
12024       (clobber (reg:CC FLAGS_REG))])
12025    (parallel
12026      [(set (match_dup 0) (xor:SWI248 (match_dup 0) (match_dup 2)))
12027       (clobber (reg:CC FLAGS_REG))])]
12028   ""
12029 {
12030   if (TARGET_LZCNT)
12031     {
12032       emit_insn (gen_clz<mode>2_lzcnt (operands[0], operands[1]));
12033       DONE;
12034     }
12035   operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
12036 })
12037
12038 (define_insn "clz<mode>2_lzcnt"
12039   [(set (match_operand:SWI248 0 "register_operand" "=r")
12040         (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12041    (clobber (reg:CC FLAGS_REG))]
12042   "TARGET_LZCNT"
12043   "lzcnt{<imodesuffix>}\t{%1, %0|%0, %1}"
12044   [(set_attr "prefix_rep" "1")
12045    (set_attr "type" "bitmanip")
12046    (set_attr "mode" "<MODE>")])
12047
12048 ;; BMI instructions.
12049 (define_insn "*bmi_andn_<mode>"
12050   [(set (match_operand:SWI48 0 "register_operand" "=r")
12051         (and:SWI48
12052           (not:SWI48
12053             (match_operand:SWI48 1 "register_operand" "r"))
12054             (match_operand:SWI48 2 "nonimmediate_operand" "rm")))
12055    (clobber (reg:CC FLAGS_REG))]
12056   "TARGET_BMI"
12057   "andn\t{%2, %1, %0|%0, %1, %2}"
12058   [(set_attr "type" "bitmanip")
12059    (set_attr "mode" "<MODE>")])
12060
12061 (define_insn "bmi_bextr_<mode>"
12062   [(set (match_operand:SWI48 0 "register_operand" "=r")
12063         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12064                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12065                        UNSPEC_BEXTR))
12066    (clobber (reg:CC FLAGS_REG))]
12067   "TARGET_BMI"
12068   "bextr\t{%2, %1, %0|%0, %1, %2}"
12069   [(set_attr "type" "bitmanip")
12070    (set_attr "mode" "<MODE>")])
12071
12072 (define_insn "*bmi_blsi_<mode>"
12073   [(set (match_operand:SWI48 0 "register_operand" "=r")
12074         (and:SWI48
12075           (neg:SWI48
12076             (match_operand:SWI48 1 "nonimmediate_operand" "rm"))
12077           (match_dup 1)))
12078    (clobber (reg:CC FLAGS_REG))]
12079   "TARGET_BMI"
12080   "blsi\t{%1, %0|%0, %1}"
12081   [(set_attr "type" "bitmanip")
12082    (set_attr "mode" "<MODE>")])
12083
12084 (define_insn "*bmi_blsmsk_<mode>"
12085   [(set (match_operand:SWI48 0 "register_operand" "=r")
12086         (xor:SWI48
12087           (plus:SWI48
12088             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12089             (const_int -1))
12090           (match_dup 1)))
12091    (clobber (reg:CC FLAGS_REG))]
12092   "TARGET_BMI"
12093   "blsmsk\t{%1, %0|%0, %1}"
12094   [(set_attr "type" "bitmanip")
12095    (set_attr "mode" "<MODE>")])
12096
12097 (define_insn "*bmi_blsr_<mode>"
12098   [(set (match_operand:SWI48 0 "register_operand" "=r")
12099         (and:SWI48
12100           (plus:SWI48
12101             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12102             (const_int -1))
12103           (match_dup 1)))
12104    (clobber (reg:CC FLAGS_REG))]
12105    "TARGET_BMI"
12106    "blsr\t{%1, %0|%0, %1}"
12107   [(set_attr "type" "bitmanip")
12108    (set_attr "mode" "<MODE>")])
12109
12110 ;; BMI2 instructions.
12111 (define_insn "bmi2_bzhi_<mode>3"
12112   [(set (match_operand:SWI48 0 "register_operand" "=r")
12113         (and:SWI48 (match_operand:SWI48 1 "register_operand" "r")
12114                    (lshiftrt:SWI48 (const_int -1)
12115                                    (match_operand:SWI48 2 "nonimmediate_operand" "rm"))))
12116    (clobber (reg:CC FLAGS_REG))]
12117   "TARGET_BMI2"
12118   "bzhi\t{%2, %1, %0|%0, %1, %2}"
12119   [(set_attr "type" "bitmanip")
12120    (set_attr "prefix" "vex")
12121    (set_attr "mode" "<MODE>")])
12122
12123 (define_insn "bmi2_pdep_<mode>3"
12124   [(set (match_operand:SWI48 0 "register_operand" "=r")
12125         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12126                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12127                        UNSPEC_PDEP))]
12128   "TARGET_BMI2"
12129   "pdep\t{%2, %1, %0|%0, %1, %2}"
12130   [(set_attr "type" "bitmanip")
12131    (set_attr "prefix" "vex")
12132    (set_attr "mode" "<MODE>")])
12133
12134 (define_insn "bmi2_pext_<mode>3"
12135   [(set (match_operand:SWI48 0 "register_operand" "=r")
12136         (unspec:SWI48 [(match_operand:SWI48 1 "register_operand" "r")
12137                        (match_operand:SWI48 2 "nonimmediate_operand" "rm")]
12138                        UNSPEC_PEXT))]
12139   "TARGET_BMI2"
12140   "pext\t{%2, %1, %0|%0, %1, %2}"
12141   [(set_attr "type" "bitmanip")
12142    (set_attr "prefix" "vex")
12143    (set_attr "mode" "<MODE>")])
12144
12145 ;; TBM instructions.
12146 (define_insn "tbm_bextri_<mode>"
12147   [(set (match_operand:SWI48 0 "register_operand" "=r")
12148         (zero_extract:SWI48
12149           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12150           (match_operand:SWI48 2 "const_0_to_255_operand" "n")
12151           (match_operand:SWI48 3 "const_0_to_255_operand" "n")))
12152    (clobber (reg:CC FLAGS_REG))]
12153    "TARGET_TBM"
12154 {
12155   operands[2] = GEN_INT (INTVAL (operands[2]) << 8 | INTVAL (operands[3]));
12156   return "bextr\t{%2, %1, %0|%0, %1, %2}";
12157 }
12158   [(set_attr "type" "bitmanip")
12159    (set_attr "mode" "<MODE>")])
12160
12161 (define_insn "*tbm_blcfill_<mode>"
12162   [(set (match_operand:SWI48 0 "register_operand" "=r")
12163         (and:SWI48
12164           (plus:SWI48
12165             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12166             (const_int 1))
12167           (match_dup 1)))
12168    (clobber (reg:CC FLAGS_REG))]
12169    "TARGET_TBM"
12170    "blcfill\t{%1, %0|%0, %1}"
12171   [(set_attr "type" "bitmanip")
12172    (set_attr "mode" "<MODE>")])
12173
12174 (define_insn "*tbm_blci_<mode>"
12175   [(set (match_operand:SWI48 0 "register_operand" "=r")
12176         (ior:SWI48
12177           (not:SWI48
12178             (plus:SWI48
12179               (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12180               (const_int 1)))
12181           (match_dup 1)))
12182    (clobber (reg:CC FLAGS_REG))]
12183    "TARGET_TBM"
12184    "blci\t{%1, %0|%0, %1}"
12185   [(set_attr "type" "bitmanip")
12186    (set_attr "mode" "<MODE>")])
12187
12188 (define_insn "*tbm_blcic_<mode>"
12189   [(set (match_operand:SWI48 0 "register_operand" "=r")
12190         (and:SWI48
12191           (plus:SWI48
12192             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12193             (const_int 1))
12194           (not:SWI48
12195             (match_dup 1))))
12196    (clobber (reg:CC FLAGS_REG))]
12197    "TARGET_TBM"
12198    "blcic\t{%1, %0|%0, %1}"
12199   [(set_attr "type" "bitmanip")
12200    (set_attr "mode" "<MODE>")])
12201
12202 (define_insn "*tbm_blcmsk_<mode>"
12203   [(set (match_operand:SWI48 0 "register_operand" "=r")
12204         (xor:SWI48
12205           (plus:SWI48
12206             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12207             (const_int 1))
12208           (match_dup 1)))
12209    (clobber (reg:CC FLAGS_REG))]
12210    "TARGET_TBM"
12211    "blcmsk\t{%1, %0|%0, %1}"
12212   [(set_attr "type" "bitmanip")
12213    (set_attr "mode" "<MODE>")])
12214
12215 (define_insn "*tbm_blcs_<mode>"
12216   [(set (match_operand:SWI48 0 "register_operand" "=r")
12217         (ior:SWI48
12218           (plus:SWI48
12219             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12220             (const_int 1))
12221           (match_dup 1)))
12222    (clobber (reg:CC FLAGS_REG))]
12223    "TARGET_TBM"
12224    "blcs\t{%1, %0|%0, %1}"
12225   [(set_attr "type" "bitmanip")
12226    (set_attr "mode" "<MODE>")])
12227
12228 (define_insn "*tbm_blsfill_<mode>"
12229   [(set (match_operand:SWI48 0 "register_operand" "=r")
12230         (ior:SWI48
12231           (plus:SWI48
12232             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12233             (const_int -1))
12234           (match_dup 1)))
12235    (clobber (reg:CC FLAGS_REG))]
12236    "TARGET_TBM"
12237    "blsfill\t{%1, %0|%0, %1}"
12238   [(set_attr "type" "bitmanip")
12239    (set_attr "mode" "<MODE>")])
12240
12241 (define_insn "*tbm_blsic_<mode>"
12242   [(set (match_operand:SWI48 0 "register_operand" "=r")
12243         (ior:SWI48
12244           (plus:SWI48
12245             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12246             (const_int -1))
12247           (not:SWI48
12248             (match_dup 1))))
12249    (clobber (reg:CC FLAGS_REG))]
12250    "TARGET_TBM"
12251    "blsic\t{%1, %0|%0, %1}"
12252   [(set_attr "type" "bitmanip")
12253    (set_attr "mode" "<MODE>")])
12254
12255 (define_insn "*tbm_t1mskc_<mode>"
12256   [(set (match_operand:SWI48 0 "register_operand" "=r")
12257         (ior:SWI48
12258           (plus:SWI48
12259             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12260             (const_int 1))
12261           (not:SWI48
12262             (match_dup 1))))
12263    (clobber (reg:CC FLAGS_REG))]
12264    "TARGET_TBM"
12265    "t1mskc\t{%1, %0|%0, %1}"
12266   [(set_attr "type" "bitmanip")
12267    (set_attr "mode" "<MODE>")])
12268
12269 (define_insn "*tbm_tzmsk_<mode>"
12270   [(set (match_operand:SWI48 0 "register_operand" "=r")
12271         (and:SWI48
12272           (plus:SWI48
12273             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12274             (const_int -1))
12275           (not:SWI48
12276             (match_dup 1))))
12277    (clobber (reg:CC FLAGS_REG))]
12278    "TARGET_TBM"
12279    "tzmsk\t{%1, %0|%0, %1}"
12280   [(set_attr "type" "bitmanip")
12281    (set_attr "mode" "<MODE>")])
12282
12283 (define_insn "bsr_rex64"
12284   [(set (match_operand:DI 0 "register_operand" "=r")
12285         (minus:DI (const_int 63)
12286                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
12287    (clobber (reg:CC FLAGS_REG))]
12288   "TARGET_64BIT"
12289   "bsr{q}\t{%1, %0|%0, %1}"
12290   [(set_attr "type" "alu1")
12291    (set_attr "prefix_0f" "1")
12292    (set_attr "mode" "DI")])
12293
12294 (define_insn "bsr"
12295   [(set (match_operand:SI 0 "register_operand" "=r")
12296         (minus:SI (const_int 31)
12297                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
12298    (clobber (reg:CC FLAGS_REG))]
12299   ""
12300   "bsr{l}\t{%1, %0|%0, %1}"
12301   [(set_attr "type" "alu1")
12302    (set_attr "prefix_0f" "1")
12303    (set_attr "mode" "SI")])
12304
12305 (define_insn "*bsrhi"
12306   [(set (match_operand:HI 0 "register_operand" "=r")
12307         (minus:HI (const_int 15)
12308                   (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
12309    (clobber (reg:CC FLAGS_REG))]
12310   ""
12311   "bsr{w}\t{%1, %0|%0, %1}"
12312   [(set_attr "type" "alu1")
12313    (set_attr "prefix_0f" "1")
12314    (set_attr "mode" "HI")])
12315
12316 (define_insn "popcount<mode>2"
12317   [(set (match_operand:SWI248 0 "register_operand" "=r")
12318         (popcount:SWI248
12319           (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12320    (clobber (reg:CC FLAGS_REG))]
12321   "TARGET_POPCNT"
12322 {
12323 #if TARGET_MACHO
12324   return "popcnt\t{%1, %0|%0, %1}";
12325 #else
12326   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12327 #endif
12328 }
12329   [(set_attr "prefix_rep" "1")
12330    (set_attr "type" "bitmanip")
12331    (set_attr "mode" "<MODE>")])
12332
12333 (define_insn "*popcount<mode>2_cmp"
12334   [(set (reg FLAGS_REG)
12335         (compare
12336           (popcount:SWI248
12337             (match_operand:SWI248 1 "nonimmediate_operand" "rm"))
12338           (const_int 0)))
12339    (set (match_operand:SWI248 0 "register_operand" "=r")
12340         (popcount:SWI248 (match_dup 1)))]
12341   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12342 {
12343 #if TARGET_MACHO
12344   return "popcnt\t{%1, %0|%0, %1}";
12345 #else
12346   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12347 #endif
12348 }
12349   [(set_attr "prefix_rep" "1")
12350    (set_attr "type" "bitmanip")
12351    (set_attr "mode" "<MODE>")])
12352
12353 (define_insn "*popcountsi2_cmp_zext"
12354   [(set (reg FLAGS_REG)
12355         (compare
12356           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
12357           (const_int 0)))
12358    (set (match_operand:DI 0 "register_operand" "=r")
12359         (zero_extend:DI(popcount:SI (match_dup 1))))]
12360   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12361 {
12362 #if TARGET_MACHO
12363   return "popcnt\t{%1, %0|%0, %1}";
12364 #else
12365   return "popcnt{l}\t{%1, %0|%0, %1}";
12366 #endif
12367 }
12368   [(set_attr "prefix_rep" "1")
12369    (set_attr "type" "bitmanip")
12370    (set_attr "mode" "SI")])
12371
12372 (define_expand "bswap<mode>2"
12373   [(set (match_operand:SWI48 0 "register_operand" "")
12374         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "")))]
12375   ""
12376 {
12377   if (<MODE>mode == SImode && !(TARGET_BSWAP || TARGET_MOVBE))
12378     {
12379       rtx x = operands[0];
12380
12381       emit_move_insn (x, operands[1]);
12382       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12383       emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
12384       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12385       DONE;
12386     }
12387 })
12388
12389 (define_insn "*bswap<mode>2_movbe"
12390   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,r,m")
12391         (bswap:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,m,r")))]
12392   "TARGET_MOVBE
12393    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12394   "@
12395     bswap\t%0
12396     movbe\t{%1, %0|%0, %1}
12397     movbe\t{%1, %0|%0, %1}"
12398   [(set_attr "type" "bitmanip,imov,imov")
12399    (set_attr "modrm" "0,1,1")
12400    (set_attr "prefix_0f" "*,1,1")
12401    (set_attr "prefix_extra" "*,1,1")
12402    (set_attr "mode" "<MODE>")])
12403
12404 (define_insn "*bswap<mode>2_1"
12405   [(set (match_operand:SWI48 0 "register_operand" "=r")
12406         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "0")))]
12407   "TARGET_BSWAP"
12408   "bswap\t%0"
12409   [(set_attr "type" "bitmanip")
12410    (set_attr "modrm" "0")
12411    (set_attr "mode" "<MODE>")])
12412
12413 (define_insn "*bswaphi_lowpart_1"
12414   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
12415         (bswap:HI (match_dup 0)))
12416    (clobber (reg:CC FLAGS_REG))]
12417   "TARGET_USE_XCHGB || optimize_function_for_size_p (cfun)"
12418   "@
12419     xchg{b}\t{%h0, %b0|%b0, %h0}
12420     rol{w}\t{$8, %0|%0, 8}"
12421   [(set_attr "length" "2,4")
12422    (set_attr "mode" "QI,HI")])
12423
12424 (define_insn "bswaphi_lowpart"
12425   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
12426         (bswap:HI (match_dup 0)))
12427    (clobber (reg:CC FLAGS_REG))]
12428   ""
12429   "rol{w}\t{$8, %0|%0, 8}"
12430   [(set_attr "length" "4")
12431    (set_attr "mode" "HI")])
12432
12433 (define_expand "paritydi2"
12434   [(set (match_operand:DI 0 "register_operand" "")
12435         (parity:DI (match_operand:DI 1 "register_operand" "")))]
12436   "! TARGET_POPCNT"
12437 {
12438   rtx scratch = gen_reg_rtx (QImode);
12439   rtx cond;
12440
12441   emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
12442                                 NULL_RTX, operands[1]));
12443
12444   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12445                          gen_rtx_REG (CCmode, FLAGS_REG),
12446                          const0_rtx);
12447   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12448
12449   if (TARGET_64BIT)
12450     emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
12451   else
12452     {
12453       rtx tmp = gen_reg_rtx (SImode);
12454
12455       emit_insn (gen_zero_extendqisi2 (tmp, scratch));
12456       emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
12457     }
12458   DONE;
12459 })
12460
12461 (define_expand "paritysi2"
12462   [(set (match_operand:SI 0 "register_operand" "")
12463         (parity:SI (match_operand:SI 1 "register_operand" "")))]
12464   "! TARGET_POPCNT"
12465 {
12466   rtx scratch = gen_reg_rtx (QImode);
12467   rtx cond;
12468
12469   emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
12470
12471   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12472                          gen_rtx_REG (CCmode, FLAGS_REG),
12473                          const0_rtx);
12474   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12475
12476   emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
12477   DONE;
12478 })
12479
12480 (define_insn_and_split "paritydi2_cmp"
12481   [(set (reg:CC FLAGS_REG)
12482         (unspec:CC [(match_operand:DI 3 "register_operand" "0")]
12483                    UNSPEC_PARITY))
12484    (clobber (match_scratch:DI 0 "=r"))
12485    (clobber (match_scratch:SI 1 "=&r"))
12486    (clobber (match_scratch:HI 2 "=Q"))]
12487   "! TARGET_POPCNT"
12488   "#"
12489   "&& reload_completed"
12490   [(parallel
12491      [(set (match_dup 1)
12492            (xor:SI (match_dup 1) (match_dup 4)))
12493       (clobber (reg:CC FLAGS_REG))])
12494    (parallel
12495      [(set (reg:CC FLAGS_REG)
12496            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12497       (clobber (match_dup 1))
12498       (clobber (match_dup 2))])]
12499 {
12500   operands[4] = gen_lowpart (SImode, operands[3]);
12501
12502   if (TARGET_64BIT)
12503     {
12504       emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
12505       emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
12506     }
12507   else
12508     operands[1] = gen_highpart (SImode, operands[3]);
12509 })
12510
12511 (define_insn_and_split "paritysi2_cmp"
12512   [(set (reg:CC FLAGS_REG)
12513         (unspec:CC [(match_operand:SI 2 "register_operand" "0")]
12514                    UNSPEC_PARITY))
12515    (clobber (match_scratch:SI 0 "=r"))
12516    (clobber (match_scratch:HI 1 "=&Q"))]
12517   "! TARGET_POPCNT"
12518   "#"
12519   "&& reload_completed"
12520   [(parallel
12521      [(set (match_dup 1)
12522            (xor:HI (match_dup 1) (match_dup 3)))
12523       (clobber (reg:CC FLAGS_REG))])
12524    (parallel
12525      [(set (reg:CC FLAGS_REG)
12526            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12527       (clobber (match_dup 1))])]
12528 {
12529   operands[3] = gen_lowpart (HImode, operands[2]);
12530
12531   emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
12532   emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
12533 })
12534
12535 (define_insn "*parityhi2_cmp"
12536   [(set (reg:CC FLAGS_REG)
12537         (unspec:CC [(match_operand:HI 1 "register_operand" "0")]
12538                    UNSPEC_PARITY))
12539    (clobber (match_scratch:HI 0 "=Q"))]
12540   "! TARGET_POPCNT"
12541   "xor{b}\t{%h0, %b0|%b0, %h0}"
12542   [(set_attr "length" "2")
12543    (set_attr "mode" "HI")])
12544
12545 \f
12546 ;; Thread-local storage patterns for ELF.
12547 ;;
12548 ;; Note that these code sequences must appear exactly as shown
12549 ;; in order to allow linker relaxation.
12550
12551 (define_insn "*tls_global_dynamic_32_gnu"
12552   [(set (match_operand:SI 0 "register_operand" "=a")
12553         (unspec:SI
12554          [(match_operand:SI 1 "register_operand" "b")
12555           (match_operand:SI 2 "tls_symbolic_operand" "")
12556           (match_operand:SI 3 "constant_call_address_operand" "z")]
12557          UNSPEC_TLS_GD))
12558    (clobber (match_scratch:SI 4 "=d"))
12559    (clobber (match_scratch:SI 5 "=c"))
12560    (clobber (reg:CC FLAGS_REG))]
12561   "!TARGET_64BIT && TARGET_GNU_TLS"
12562 {
12563   output_asm_insn
12564     ("lea{l}\t{%E2@tlsgd(,%1,1), %0|%0, %E2@tlsgd[%1*1]}", operands);
12565   if (TARGET_SUN_TLS)
12566 #ifdef HAVE_AS_IX86_TLSGDPLT
12567     return "call\t%a2@tlsgdplt";
12568 #else
12569     return "call\t%p3@plt";
12570 #endif
12571   return "call\t%P3";
12572 }
12573   [(set_attr "type" "multi")
12574    (set_attr "length" "12")])
12575
12576 (define_expand "tls_global_dynamic_32"
12577   [(parallel
12578     [(set (match_operand:SI 0 "register_operand" "")
12579           (unspec:SI [(match_operand:SI 2 "register_operand" "")
12580                       (match_operand:SI 1 "tls_symbolic_operand" "")
12581                       (match_operand:SI 3 "constant_call_address_operand" "")]
12582                      UNSPEC_TLS_GD))
12583      (clobber (match_scratch:SI 4 ""))
12584      (clobber (match_scratch:SI 5 ""))
12585      (clobber (reg:CC FLAGS_REG))])])
12586
12587 (define_insn "*tls_global_dynamic_64"
12588   [(set (match_operand:DI 0 "register_operand" "=a")
12589         (call:DI
12590          (mem:QI (match_operand:DI 2 "constant_call_address_operand" "z"))
12591          (match_operand:DI 3 "" "")))
12592    (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12593               UNSPEC_TLS_GD)]
12594   "TARGET_64BIT"
12595 {
12596   if (!TARGET_X32)
12597     fputs (ASM_BYTE "0x66\n", asm_out_file);
12598   output_asm_insn
12599     ("lea{q}\t{%E1@tlsgd(%%rip), %%rdi|rdi, %E1@tlsgd[rip]}", operands);
12600   fputs (ASM_SHORT "0x6666\n", asm_out_file);
12601   fputs ("\trex64\n", asm_out_file);
12602   if (TARGET_SUN_TLS)
12603     return "call\t%p2@plt";
12604   return "call\t%P2";
12605 }
12606   [(set_attr "type" "multi")
12607    (set (attr "length")
12608         (symbol_ref "TARGET_X32 ? 15 : 16"))])
12609
12610 (define_expand "tls_global_dynamic_64"
12611   [(parallel
12612     [(set (match_operand:DI 0 "register_operand" "")
12613           (call:DI
12614            (mem:QI (match_operand:DI 2 "constant_call_address_operand" ""))
12615            (const_int 0)))
12616      (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12617                 UNSPEC_TLS_GD)])])
12618
12619 (define_insn "*tls_local_dynamic_base_32_gnu"
12620   [(set (match_operand:SI 0 "register_operand" "=a")
12621         (unspec:SI
12622          [(match_operand:SI 1 "register_operand" "b")
12623           (match_operand:SI 2 "constant_call_address_operand" "z")]
12624          UNSPEC_TLS_LD_BASE))
12625    (clobber (match_scratch:SI 3 "=d"))
12626    (clobber (match_scratch:SI 4 "=c"))
12627    (clobber (reg:CC FLAGS_REG))]
12628   "!TARGET_64BIT && TARGET_GNU_TLS"
12629 {
12630   output_asm_insn
12631     ("lea{l}\t{%&@tlsldm(%1), %0|%0, %&@tlsldm[%1]}", operands);
12632   if (TARGET_SUN_TLS)
12633 #ifdef HAVE_AS_IX86_TLSLDMPLT
12634     return "call\t%&@tlsldmplt";
12635 #else
12636     return "call\t%p2@plt";
12637 #endif
12638   return "call\t%P2";
12639 }
12640   [(set_attr "type" "multi")
12641    (set_attr "length" "11")])
12642
12643 (define_expand "tls_local_dynamic_base_32"
12644   [(parallel
12645      [(set (match_operand:SI 0 "register_operand" "")
12646            (unspec:SI
12647             [(match_operand:SI 1 "register_operand" "")
12648              (match_operand:SI 2 "constant_call_address_operand" "")]
12649             UNSPEC_TLS_LD_BASE))
12650       (clobber (match_scratch:SI 3 ""))
12651       (clobber (match_scratch:SI 4 ""))
12652       (clobber (reg:CC FLAGS_REG))])])
12653
12654 (define_insn "*tls_local_dynamic_base_64"
12655   [(set (match_operand:DI 0 "register_operand" "=a")
12656         (call:DI
12657          (mem:QI (match_operand:DI 1 "constant_call_address_operand" "z"))
12658          (match_operand:DI 2 "" "")))
12659    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
12660   "TARGET_64BIT"
12661 {
12662   output_asm_insn
12663     ("lea{q}\t{%&@tlsld(%%rip), %%rdi|rdi, %&@tlsld[rip]}", operands);
12664   if (TARGET_SUN_TLS)
12665     return "call\t%p1@plt";
12666   return "call\t%P1";
12667 }
12668   [(set_attr "type" "multi")
12669    (set_attr "length" "12")])
12670
12671 (define_expand "tls_local_dynamic_base_64"
12672   [(parallel
12673      [(set (match_operand:DI 0 "register_operand" "")
12674            (call:DI
12675             (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
12676             (const_int 0)))
12677       (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])])
12678
12679 ;; Local dynamic of a single variable is a lose.  Show combine how
12680 ;; to convert that back to global dynamic.
12681
12682 (define_insn_and_split "*tls_local_dynamic_32_once"
12683   [(set (match_operand:SI 0 "register_operand" "=a")
12684         (plus:SI
12685          (unspec:SI [(match_operand:SI 1 "register_operand" "b")
12686                      (match_operand:SI 2 "constant_call_address_operand" "z")]
12687                     UNSPEC_TLS_LD_BASE)
12688          (const:SI (unspec:SI
12689                     [(match_operand:SI 3 "tls_symbolic_operand" "")]
12690                     UNSPEC_DTPOFF))))
12691    (clobber (match_scratch:SI 4 "=d"))
12692    (clobber (match_scratch:SI 5 "=c"))
12693    (clobber (reg:CC FLAGS_REG))]
12694   ""
12695   "#"
12696   ""
12697   [(parallel
12698      [(set (match_dup 0)
12699            (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
12700                       UNSPEC_TLS_GD))
12701       (clobber (match_dup 4))
12702       (clobber (match_dup 5))
12703       (clobber (reg:CC FLAGS_REG))])])
12704
12705 ;; Segment register for the thread base ptr load
12706 (define_mode_attr tp_seg [(SI "gs") (DI "fs")])
12707
12708 ;; Load and add the thread base pointer from %<tp_seg>:0.
12709 (define_insn "*load_tp_x32"
12710   [(set (match_operand:SI 0 "register_operand" "=r")
12711         (unspec:SI [(const_int 0)] UNSPEC_TP))]
12712   "TARGET_X32"
12713   "mov{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12714   [(set_attr "type" "imov")
12715    (set_attr "modrm" "0")
12716    (set_attr "length" "7")
12717    (set_attr "memory" "load")
12718    (set_attr "imm_disp" "false")])
12719
12720 (define_insn "*load_tp_x32_zext"
12721   [(set (match_operand:DI 0 "register_operand" "=r")
12722         (zero_extend:DI (unspec:SI [(const_int 0)] UNSPEC_TP)))]
12723   "TARGET_X32"
12724   "mov{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12725   [(set_attr "type" "imov")
12726    (set_attr "modrm" "0")
12727    (set_attr "length" "7")
12728    (set_attr "memory" "load")
12729    (set_attr "imm_disp" "false")])
12730
12731 (define_insn "*load_tp_<mode>"
12732   [(set (match_operand:P 0 "register_operand" "=r")
12733         (unspec:P [(const_int 0)] UNSPEC_TP))]
12734   "!TARGET_X32"
12735   "mov{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12736   [(set_attr "type" "imov")
12737    (set_attr "modrm" "0")
12738    (set_attr "length" "7")
12739    (set_attr "memory" "load")
12740    (set_attr "imm_disp" "false")])
12741
12742 (define_insn "*add_tp_x32"
12743   [(set (match_operand:SI 0 "register_operand" "=r")
12744         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12745                  (match_operand:SI 1 "register_operand" "0")))
12746    (clobber (reg:CC FLAGS_REG))]
12747   "TARGET_X32"
12748   "add{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12749   [(set_attr "type" "alu")
12750    (set_attr "modrm" "0")
12751    (set_attr "length" "7")
12752    (set_attr "memory" "load")
12753    (set_attr "imm_disp" "false")])
12754
12755 (define_insn "*add_tp_x32_zext"
12756   [(set (match_operand:DI 0 "register_operand" "=r")
12757         (zero_extend:DI
12758           (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12759                    (match_operand:SI 1 "register_operand" "0"))))
12760    (clobber (reg:CC FLAGS_REG))]
12761   "TARGET_X32"
12762   "add{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12763   [(set_attr "type" "alu")
12764    (set_attr "modrm" "0")
12765    (set_attr "length" "7")
12766    (set_attr "memory" "load")
12767    (set_attr "imm_disp" "false")])
12768
12769 (define_insn "*add_tp_<mode>"
12770   [(set (match_operand:P 0 "register_operand" "=r")
12771         (plus:P (unspec:P [(const_int 0)] UNSPEC_TP)
12772                 (match_operand:P 1 "register_operand" "0")))
12773    (clobber (reg:CC FLAGS_REG))]
12774   "!TARGET_X32"
12775   "add{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12776   [(set_attr "type" "alu")
12777    (set_attr "modrm" "0")
12778    (set_attr "length" "7")
12779    (set_attr "memory" "load")
12780    (set_attr "imm_disp" "false")])
12781
12782 ;; The Sun linker took the AMD64 TLS spec literally and can only handle
12783 ;; %rax as destination of the initial executable code sequence.
12784 (define_insn "tls_initial_exec_64_sun"
12785   [(set (match_operand:DI 0 "register_operand" "=a")
12786         (unspec:DI
12787          [(match_operand:DI 1 "tls_symbolic_operand" "")]
12788          UNSPEC_TLS_IE_SUN))
12789    (clobber (reg:CC FLAGS_REG))]
12790   "TARGET_64BIT && TARGET_SUN_TLS"
12791 {
12792   output_asm_insn
12793     ("mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}", operands);
12794   return "add{q}\t{%a1@gottpoff(%%rip), %0|%0, %a1@gottpoff[rip]}";
12795 }
12796   [(set_attr "type" "multi")])
12797
12798 ;; GNU2 TLS patterns can be split.
12799
12800 (define_expand "tls_dynamic_gnu2_32"
12801   [(set (match_dup 3)
12802         (plus:SI (match_operand:SI 2 "register_operand" "")
12803                  (const:SI
12804                   (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
12805                              UNSPEC_TLSDESC))))
12806    (parallel
12807     [(set (match_operand:SI 0 "register_operand" "")
12808           (unspec:SI [(match_dup 1) (match_dup 3)
12809                       (match_dup 2) (reg:SI SP_REG)]
12810                       UNSPEC_TLSDESC))
12811      (clobber (reg:CC FLAGS_REG))])]
12812   "!TARGET_64BIT && TARGET_GNU2_TLS"
12813 {
12814   operands[3] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12815   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12816 })
12817
12818 (define_insn "*tls_dynamic_gnu2_lea_32"
12819   [(set (match_operand:SI 0 "register_operand" "=r")
12820         (plus:SI (match_operand:SI 1 "register_operand" "b")
12821                  (const:SI
12822                   (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
12823                               UNSPEC_TLSDESC))))]
12824   "!TARGET_64BIT && TARGET_GNU2_TLS"
12825   "lea{l}\t{%E2@TLSDESC(%1), %0|%0, %E2@TLSDESC[%1]}"
12826   [(set_attr "type" "lea")
12827    (set_attr "mode" "SI")
12828    (set_attr "length" "6")
12829    (set_attr "length_address" "4")])
12830
12831 (define_insn "*tls_dynamic_gnu2_call_32"
12832   [(set (match_operand:SI 0 "register_operand" "=a")
12833         (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
12834                     (match_operand:SI 2 "register_operand" "0")
12835                     ;; we have to make sure %ebx still points to the GOT
12836                     (match_operand:SI 3 "register_operand" "b")
12837                     (reg:SI SP_REG)]
12838                    UNSPEC_TLSDESC))
12839    (clobber (reg:CC FLAGS_REG))]
12840   "!TARGET_64BIT && TARGET_GNU2_TLS"
12841   "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
12842   [(set_attr "type" "call")
12843    (set_attr "length" "2")
12844    (set_attr "length_address" "0")])
12845
12846 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
12847   [(set (match_operand:SI 0 "register_operand" "=&a")
12848         (plus:SI
12849          (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
12850                      (match_operand:SI 4 "" "")
12851                      (match_operand:SI 2 "register_operand" "b")
12852                      (reg:SI SP_REG)]
12853                     UNSPEC_TLSDESC)
12854          (const:SI (unspec:SI
12855                     [(match_operand:SI 1 "tls_symbolic_operand" "")]
12856                     UNSPEC_DTPOFF))))
12857    (clobber (reg:CC FLAGS_REG))]
12858   "!TARGET_64BIT && TARGET_GNU2_TLS"
12859   "#"
12860   ""
12861   [(set (match_dup 0) (match_dup 5))]
12862 {
12863   operands[5] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12864   emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
12865 })
12866
12867 (define_expand "tls_dynamic_gnu2_64"
12868   [(set (match_dup 2)
12869         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12870                    UNSPEC_TLSDESC))
12871    (parallel
12872     [(set (match_operand:DI 0 "register_operand" "")
12873           (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
12874                      UNSPEC_TLSDESC))
12875      (clobber (reg:CC FLAGS_REG))])]
12876   "TARGET_64BIT && TARGET_GNU2_TLS"
12877 {
12878   operands[2] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12879   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12880 })
12881
12882 (define_insn "*tls_dynamic_gnu2_lea_64"
12883   [(set (match_operand:DI 0 "register_operand" "=r")
12884         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12885                    UNSPEC_TLSDESC))]
12886   "TARGET_64BIT && TARGET_GNU2_TLS"
12887   "lea{q}\t{%E1@TLSDESC(%%rip), %0|%0, %E1@TLSDESC[rip]}"
12888   [(set_attr "type" "lea")
12889    (set_attr "mode" "DI")
12890    (set_attr "length" "7")
12891    (set_attr "length_address" "4")])
12892
12893 (define_insn "*tls_dynamic_gnu2_call_64"
12894   [(set (match_operand:DI 0 "register_operand" "=a")
12895         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")
12896                     (match_operand:DI 2 "register_operand" "0")
12897                     (reg:DI SP_REG)]
12898                    UNSPEC_TLSDESC))
12899    (clobber (reg:CC FLAGS_REG))]
12900   "TARGET_64BIT && TARGET_GNU2_TLS"
12901   "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
12902   [(set_attr "type" "call")
12903    (set_attr "length" "2")
12904    (set_attr "length_address" "0")])
12905
12906 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
12907   [(set (match_operand:DI 0 "register_operand" "=&a")
12908         (plus:DI
12909          (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
12910                      (match_operand:DI 3 "" "")
12911                      (reg:DI SP_REG)]
12912                     UNSPEC_TLSDESC)
12913          (const:DI (unspec:DI
12914                     [(match_operand 1 "tls_symbolic_operand" "")]
12915                     UNSPEC_DTPOFF))))
12916    (clobber (reg:CC FLAGS_REG))]
12917   "TARGET_64BIT && TARGET_GNU2_TLS"
12918   "#"
12919   ""
12920   [(set (match_dup 0) (match_dup 4))]
12921 {
12922   operands[4] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12923   emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
12924 })
12925 \f
12926 ;; These patterns match the binary 387 instructions for addM3, subM3,
12927 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
12928 ;; SFmode.  The first is the normal insn, the second the same insn but
12929 ;; with one operand a conversion, and the third the same insn but with
12930 ;; the other operand a conversion.  The conversion may be SFmode or
12931 ;; SImode if the target mode DFmode, but only SImode if the target mode
12932 ;; is SFmode.
12933
12934 ;; Gcc is slightly more smart about handling normal two address instructions
12935 ;; so use special patterns for add and mull.
12936
12937 (define_insn "*fop_<mode>_comm_mixed"
12938   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
12939         (match_operator:MODEF 3 "binary_fp_operator"
12940           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,0,x")
12941            (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm,xm")]))]
12942   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
12943    && COMMUTATIVE_ARITH_P (operands[3])
12944    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12945   "* return output_387_binary_op (insn, operands);"
12946   [(set (attr "type")
12947         (if_then_else (eq_attr "alternative" "1,2")
12948            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12949               (const_string "ssemul")
12950               (const_string "sseadd"))
12951            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12952               (const_string "fmul")
12953               (const_string "fop"))))
12954    (set_attr "isa" "*,noavx,avx")
12955    (set_attr "prefix" "orig,orig,vex")
12956    (set_attr "mode" "<MODE>")])
12957
12958 (define_insn "*fop_<mode>_comm_sse"
12959   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
12960         (match_operator:MODEF 3 "binary_fp_operator"
12961           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
12962            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
12963   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
12964    && COMMUTATIVE_ARITH_P (operands[3])
12965    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12966   "* return output_387_binary_op (insn, operands);"
12967   [(set (attr "type")
12968         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12969            (const_string "ssemul")
12970            (const_string "sseadd")))
12971    (set_attr "isa" "noavx,avx")
12972    (set_attr "prefix" "orig,vex")
12973    (set_attr "mode" "<MODE>")])
12974
12975 (define_insn "*fop_<mode>_comm_i387"
12976   [(set (match_operand:MODEF 0 "register_operand" "=f")
12977         (match_operator:MODEF 3 "binary_fp_operator"
12978           [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
12979            (match_operand:MODEF 2 "nonimmediate_operand" "fm")]))]
12980   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
12981    && COMMUTATIVE_ARITH_P (operands[3])
12982    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12983   "* return output_387_binary_op (insn, operands);"
12984   [(set (attr "type")
12985         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12986            (const_string "fmul")
12987            (const_string "fop")))
12988    (set_attr "mode" "<MODE>")])
12989
12990 (define_insn "*fop_<mode>_1_mixed"
12991   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
12992         (match_operator:MODEF 3 "binary_fp_operator"
12993           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,0,x")
12994            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm,xm")]))]
12995   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
12996    && !COMMUTATIVE_ARITH_P (operands[3])
12997    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12998   "* return output_387_binary_op (insn, operands);"
12999   [(set (attr "type")
13000         (cond [(and (eq_attr "alternative" "2,3")
13001                     (match_operand:MODEF 3 "mult_operator" ""))
13002                  (const_string "ssemul")
13003                (and (eq_attr "alternative" "2,3")
13004                     (match_operand:MODEF 3 "div_operator" ""))
13005                  (const_string "ssediv")
13006                (eq_attr "alternative" "2,3")
13007                  (const_string "sseadd")
13008                (match_operand:MODEF 3 "mult_operator" "")
13009                  (const_string "fmul")
13010                (match_operand:MODEF 3 "div_operator" "")
13011                  (const_string "fdiv")
13012               ]
13013               (const_string "fop")))
13014    (set_attr "isa" "*,*,noavx,avx")
13015    (set_attr "prefix" "orig,orig,orig,vex")
13016    (set_attr "mode" "<MODE>")])
13017
13018 (define_insn "*rcpsf2_sse"
13019   [(set (match_operand:SF 0 "register_operand" "=x")
13020         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13021                    UNSPEC_RCP))]
13022   "TARGET_SSE_MATH"
13023   "%vrcpss\t{%1, %d0|%d0, %1}"
13024   [(set_attr "type" "sse")
13025    (set_attr "atom_sse_attr" "rcp")
13026    (set_attr "prefix" "maybe_vex")
13027    (set_attr "mode" "SF")])
13028
13029 (define_insn "*fop_<mode>_1_sse"
13030   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
13031         (match_operator:MODEF 3 "binary_fp_operator"
13032           [(match_operand:MODEF 1 "register_operand" "0,x")
13033            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
13034   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13035    && !COMMUTATIVE_ARITH_P (operands[3])"
13036   "* return output_387_binary_op (insn, operands);"
13037   [(set (attr "type")
13038         (cond [(match_operand:MODEF 3 "mult_operator" "")
13039                  (const_string "ssemul")
13040                (match_operand:MODEF 3 "div_operator" "")
13041                  (const_string "ssediv")
13042               ]
13043               (const_string "sseadd")))
13044    (set_attr "isa" "noavx,avx")
13045    (set_attr "prefix" "orig,vex")
13046    (set_attr "mode" "<MODE>")])
13047
13048 ;; This pattern is not fully shadowed by the pattern above.
13049 (define_insn "*fop_<mode>_1_i387"
13050   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13051         (match_operator:MODEF 3 "binary_fp_operator"
13052           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm")
13053            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0")]))]
13054   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
13055    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13056    && !COMMUTATIVE_ARITH_P (operands[3])
13057    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13058   "* return output_387_binary_op (insn, operands);"
13059   [(set (attr "type")
13060         (cond [(match_operand:MODEF 3 "mult_operator" "")
13061                  (const_string "fmul")
13062                (match_operand:MODEF 3 "div_operator" "")
13063                  (const_string "fdiv")
13064               ]
13065               (const_string "fop")))
13066    (set_attr "mode" "<MODE>")])
13067
13068 ;; ??? Add SSE splitters for these!
13069 (define_insn "*fop_<MODEF:mode>_2_i387"
13070   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13071         (match_operator:MODEF 3 "binary_fp_operator"
13072           [(float:MODEF
13073              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13074            (match_operand:MODEF 2 "register_operand" "0,0")]))]
13075   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13076    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13077    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13078   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13079   [(set (attr "type")
13080         (cond [(match_operand:MODEF 3 "mult_operator" "")
13081                  (const_string "fmul")
13082                (match_operand:MODEF 3 "div_operator" "")
13083                  (const_string "fdiv")
13084               ]
13085               (const_string "fop")))
13086    (set_attr "fp_int_src" "true")
13087    (set_attr "mode" "<SWI24:MODE>")])
13088
13089 (define_insn "*fop_<MODEF:mode>_3_i387"
13090   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13091         (match_operator:MODEF 3 "binary_fp_operator"
13092           [(match_operand:MODEF 1 "register_operand" "0,0")
13093            (float:MODEF
13094              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13095   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13096    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13097    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13098   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13099   [(set (attr "type")
13100         (cond [(match_operand:MODEF 3 "mult_operator" "")
13101                  (const_string "fmul")
13102                (match_operand:MODEF 3 "div_operator" "")
13103                  (const_string "fdiv")
13104               ]
13105               (const_string "fop")))
13106    (set_attr "fp_int_src" "true")
13107    (set_attr "mode" "<MODE>")])
13108
13109 (define_insn "*fop_df_4_i387"
13110   [(set (match_operand:DF 0 "register_operand" "=f,f")
13111         (match_operator:DF 3 "binary_fp_operator"
13112            [(float_extend:DF
13113              (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
13114             (match_operand:DF 2 "register_operand" "0,f")]))]
13115   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13116    && !(TARGET_SSE2 && TARGET_SSE_MATH)
13117    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13118   "* return output_387_binary_op (insn, operands);"
13119   [(set (attr "type")
13120         (cond [(match_operand:DF 3 "mult_operator" "")
13121                  (const_string "fmul")
13122                (match_operand:DF 3 "div_operator" "")
13123                  (const_string "fdiv")
13124               ]
13125               (const_string "fop")))
13126    (set_attr "mode" "SF")])
13127
13128 (define_insn "*fop_df_5_i387"
13129   [(set (match_operand:DF 0 "register_operand" "=f,f")
13130         (match_operator:DF 3 "binary_fp_operator"
13131           [(match_operand:DF 1 "register_operand" "0,f")
13132            (float_extend:DF
13133             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13134   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13135    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13136   "* return output_387_binary_op (insn, operands);"
13137   [(set (attr "type")
13138         (cond [(match_operand:DF 3 "mult_operator" "")
13139                  (const_string "fmul")
13140                (match_operand:DF 3 "div_operator" "")
13141                  (const_string "fdiv")
13142               ]
13143               (const_string "fop")))
13144    (set_attr "mode" "SF")])
13145
13146 (define_insn "*fop_df_6_i387"
13147   [(set (match_operand:DF 0 "register_operand" "=f,f")
13148         (match_operator:DF 3 "binary_fp_operator"
13149           [(float_extend:DF
13150             (match_operand:SF 1 "register_operand" "0,f"))
13151            (float_extend:DF
13152             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13153   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13154    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13155   "* return output_387_binary_op (insn, operands);"
13156   [(set (attr "type")
13157         (cond [(match_operand:DF 3 "mult_operator" "")
13158                  (const_string "fmul")
13159                (match_operand:DF 3 "div_operator" "")
13160                  (const_string "fdiv")
13161               ]
13162               (const_string "fop")))
13163    (set_attr "mode" "SF")])
13164
13165 (define_insn "*fop_xf_comm_i387"
13166   [(set (match_operand:XF 0 "register_operand" "=f")
13167         (match_operator:XF 3 "binary_fp_operator"
13168                         [(match_operand:XF 1 "register_operand" "%0")
13169                          (match_operand:XF 2 "register_operand" "f")]))]
13170   "TARGET_80387
13171    && COMMUTATIVE_ARITH_P (operands[3])"
13172   "* return output_387_binary_op (insn, operands);"
13173   [(set (attr "type")
13174         (if_then_else (match_operand:XF 3 "mult_operator" "")
13175            (const_string "fmul")
13176            (const_string "fop")))
13177    (set_attr "mode" "XF")])
13178
13179 (define_insn "*fop_xf_1_i387"
13180   [(set (match_operand:XF 0 "register_operand" "=f,f")
13181         (match_operator:XF 3 "binary_fp_operator"
13182                         [(match_operand:XF 1 "register_operand" "0,f")
13183                          (match_operand:XF 2 "register_operand" "f,0")]))]
13184   "TARGET_80387
13185    && !COMMUTATIVE_ARITH_P (operands[3])"
13186   "* return output_387_binary_op (insn, operands);"
13187   [(set (attr "type")
13188         (cond [(match_operand:XF 3 "mult_operator" "")
13189                  (const_string "fmul")
13190                (match_operand:XF 3 "div_operator" "")
13191                  (const_string "fdiv")
13192               ]
13193               (const_string "fop")))
13194    (set_attr "mode" "XF")])
13195
13196 (define_insn "*fop_xf_2_i387"
13197   [(set (match_operand:XF 0 "register_operand" "=f,f")
13198         (match_operator:XF 3 "binary_fp_operator"
13199           [(float:XF
13200              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13201            (match_operand:XF 2 "register_operand" "0,0")]))]
13202   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13203   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13204   [(set (attr "type")
13205         (cond [(match_operand:XF 3 "mult_operator" "")
13206                  (const_string "fmul")
13207                (match_operand:XF 3 "div_operator" "")
13208                  (const_string "fdiv")
13209               ]
13210               (const_string "fop")))
13211    (set_attr "fp_int_src" "true")
13212    (set_attr "mode" "<MODE>")])
13213
13214 (define_insn "*fop_xf_3_i387"
13215   [(set (match_operand:XF 0 "register_operand" "=f,f")
13216         (match_operator:XF 3 "binary_fp_operator"
13217           [(match_operand:XF 1 "register_operand" "0,0")
13218            (float:XF
13219              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13220   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13221   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13222   [(set (attr "type")
13223         (cond [(match_operand:XF 3 "mult_operator" "")
13224                  (const_string "fmul")
13225                (match_operand:XF 3 "div_operator" "")
13226                  (const_string "fdiv")
13227               ]
13228               (const_string "fop")))
13229    (set_attr "fp_int_src" "true")
13230    (set_attr "mode" "<MODE>")])
13231
13232 (define_insn "*fop_xf_4_i387"
13233   [(set (match_operand:XF 0 "register_operand" "=f,f")
13234         (match_operator:XF 3 "binary_fp_operator"
13235            [(float_extend:XF
13236               (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
13237             (match_operand:XF 2 "register_operand" "0,f")]))]
13238   "TARGET_80387"
13239   "* return output_387_binary_op (insn, operands);"
13240   [(set (attr "type")
13241         (cond [(match_operand:XF 3 "mult_operator" "")
13242                  (const_string "fmul")
13243                (match_operand:XF 3 "div_operator" "")
13244                  (const_string "fdiv")
13245               ]
13246               (const_string "fop")))
13247    (set_attr "mode" "<MODE>")])
13248
13249 (define_insn "*fop_xf_5_i387"
13250   [(set (match_operand:XF 0 "register_operand" "=f,f")
13251         (match_operator:XF 3 "binary_fp_operator"
13252           [(match_operand:XF 1 "register_operand" "0,f")
13253            (float_extend:XF
13254              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13255   "TARGET_80387"
13256   "* return output_387_binary_op (insn, operands);"
13257   [(set (attr "type")
13258         (cond [(match_operand:XF 3 "mult_operator" "")
13259                  (const_string "fmul")
13260                (match_operand:XF 3 "div_operator" "")
13261                  (const_string "fdiv")
13262               ]
13263               (const_string "fop")))
13264    (set_attr "mode" "<MODE>")])
13265
13266 (define_insn "*fop_xf_6_i387"
13267   [(set (match_operand:XF 0 "register_operand" "=f,f")
13268         (match_operator:XF 3 "binary_fp_operator"
13269           [(float_extend:XF
13270              (match_operand:MODEF 1 "register_operand" "0,f"))
13271            (float_extend:XF
13272              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13273   "TARGET_80387"
13274   "* return output_387_binary_op (insn, operands);"
13275   [(set (attr "type")
13276         (cond [(match_operand:XF 3 "mult_operator" "")
13277                  (const_string "fmul")
13278                (match_operand:XF 3 "div_operator" "")
13279                  (const_string "fdiv")
13280               ]
13281               (const_string "fop")))
13282    (set_attr "mode" "<MODE>")])
13283
13284 (define_split
13285   [(set (match_operand 0 "register_operand" "")
13286         (match_operator 3 "binary_fp_operator"
13287            [(float (match_operand:SWI24 1 "register_operand" ""))
13288             (match_operand 2 "register_operand" "")]))]
13289   "reload_completed
13290    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13291    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[1]))"
13292   [(const_int 0)]
13293 {
13294   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
13295   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13296   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13297                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13298                                           GET_MODE (operands[3]),
13299                                           operands[4],
13300                                           operands[2])));
13301   ix86_free_from_memory (GET_MODE (operands[1]));
13302   DONE;
13303 })
13304
13305 (define_split
13306   [(set (match_operand 0 "register_operand" "")
13307         (match_operator 3 "binary_fp_operator"
13308            [(match_operand 1 "register_operand" "")
13309             (float (match_operand:SWI24 2 "register_operand" ""))]))]
13310   "reload_completed
13311    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13312    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[2]))"
13313   [(const_int 0)]
13314 {
13315   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13316   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13317   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13318                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13319                                           GET_MODE (operands[3]),
13320                                           operands[1],
13321                                           operands[4])));
13322   ix86_free_from_memory (GET_MODE (operands[2]));
13323   DONE;
13324 })
13325 \f
13326 ;; FPU special functions.
13327
13328 ;; This pattern implements a no-op XFmode truncation for
13329 ;; all fancy i386 XFmode math functions.
13330
13331 (define_insn "truncxf<mode>2_i387_noop_unspec"
13332   [(set (match_operand:MODEF 0 "register_operand" "=f")
13333         (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
13334         UNSPEC_TRUNC_NOOP))]
13335   "TARGET_USE_FANCY_MATH_387"
13336   "* return output_387_reg_move (insn, operands);"
13337   [(set_attr "type" "fmov")
13338    (set_attr "mode" "<MODE>")])
13339
13340 (define_insn "sqrtxf2"
13341   [(set (match_operand:XF 0 "register_operand" "=f")
13342         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
13343   "TARGET_USE_FANCY_MATH_387"
13344   "fsqrt"
13345   [(set_attr "type" "fpspc")
13346    (set_attr "mode" "XF")
13347    (set_attr "athlon_decode" "direct")
13348    (set_attr "amdfam10_decode" "direct")
13349    (set_attr "bdver1_decode" "direct")])
13350
13351 (define_insn "sqrt_extend<mode>xf2_i387"
13352   [(set (match_operand:XF 0 "register_operand" "=f")
13353         (sqrt:XF
13354           (float_extend:XF
13355             (match_operand:MODEF 1 "register_operand" "0"))))]
13356   "TARGET_USE_FANCY_MATH_387"
13357   "fsqrt"
13358   [(set_attr "type" "fpspc")
13359    (set_attr "mode" "XF")
13360    (set_attr "athlon_decode" "direct")
13361    (set_attr "amdfam10_decode" "direct")
13362    (set_attr "bdver1_decode" "direct")])
13363
13364 (define_insn "*rsqrtsf2_sse"
13365   [(set (match_operand:SF 0 "register_operand" "=x")
13366         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13367                    UNSPEC_RSQRT))]
13368   "TARGET_SSE_MATH"
13369   "%vrsqrtss\t{%1, %d0|%d0, %1}"
13370   [(set_attr "type" "sse")
13371    (set_attr "atom_sse_attr" "rcp")
13372    (set_attr "prefix" "maybe_vex")
13373    (set_attr "mode" "SF")])
13374
13375 (define_expand "rsqrtsf2"
13376   [(set (match_operand:SF 0 "register_operand" "")
13377         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
13378                    UNSPEC_RSQRT))]
13379   "TARGET_SSE_MATH"
13380 {
13381   ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
13382   DONE;
13383 })
13384
13385 (define_insn "*sqrt<mode>2_sse"
13386   [(set (match_operand:MODEF 0 "register_operand" "=x")
13387         (sqrt:MODEF
13388           (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
13389   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
13390   "%vsqrt<ssemodesuffix>\t{%1, %d0|%d0, %1}"
13391   [(set_attr "type" "sse")
13392    (set_attr "atom_sse_attr" "sqrt")
13393    (set_attr "prefix" "maybe_vex")
13394    (set_attr "mode" "<MODE>")
13395    (set_attr "athlon_decode" "*")
13396    (set_attr "amdfam10_decode" "*")
13397    (set_attr "bdver1_decode" "*")])
13398
13399 (define_expand "sqrt<mode>2"
13400   [(set (match_operand:MODEF 0 "register_operand" "")
13401         (sqrt:MODEF
13402           (match_operand:MODEF 1 "nonimmediate_operand" "")))]
13403   "(TARGET_USE_FANCY_MATH_387 && X87_ENABLE_ARITH (<MODE>mode))
13404    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
13405 {
13406   if (<MODE>mode == SFmode
13407       && TARGET_SSE_MATH
13408       && TARGET_RECIP_SQRT
13409       && !optimize_function_for_size_p (cfun)
13410       && flag_finite_math_only && !flag_trapping_math
13411       && flag_unsafe_math_optimizations)
13412     {
13413       ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
13414       DONE;
13415     }
13416
13417   if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
13418     {
13419       rtx op0 = gen_reg_rtx (XFmode);
13420       rtx op1 = force_reg (<MODE>mode, operands[1]);
13421
13422       emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
13423       emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
13424       DONE;
13425    }
13426 })
13427
13428 (define_insn "fpremxf4_i387"
13429   [(set (match_operand:XF 0 "register_operand" "=f")
13430         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13431                     (match_operand:XF 3 "register_operand" "1")]
13432                    UNSPEC_FPREM_F))
13433    (set (match_operand:XF 1 "register_operand" "=u")
13434         (unspec:XF [(match_dup 2) (match_dup 3)]
13435                    UNSPEC_FPREM_U))
13436    (set (reg:CCFP FPSR_REG)
13437         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13438                      UNSPEC_C2_FLAG))]
13439   "TARGET_USE_FANCY_MATH_387"
13440   "fprem"
13441   [(set_attr "type" "fpspc")
13442    (set_attr "mode" "XF")])
13443
13444 (define_expand "fmodxf3"
13445   [(use (match_operand:XF 0 "register_operand" ""))
13446    (use (match_operand:XF 1 "general_operand" ""))
13447    (use (match_operand:XF 2 "general_operand" ""))]
13448   "TARGET_USE_FANCY_MATH_387"
13449 {
13450   rtx label = gen_label_rtx ();
13451
13452   rtx op1 = gen_reg_rtx (XFmode);
13453   rtx op2 = gen_reg_rtx (XFmode);
13454
13455   emit_move_insn (op2, operands[2]);
13456   emit_move_insn (op1, operands[1]);
13457
13458   emit_label (label);
13459   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13460   ix86_emit_fp_unordered_jump (label);
13461   LABEL_NUSES (label) = 1;
13462
13463   emit_move_insn (operands[0], op1);
13464   DONE;
13465 })
13466
13467 (define_expand "fmod<mode>3"
13468   [(use (match_operand:MODEF 0 "register_operand" ""))
13469    (use (match_operand:MODEF 1 "general_operand" ""))
13470    (use (match_operand:MODEF 2 "general_operand" ""))]
13471   "TARGET_USE_FANCY_MATH_387"
13472 {
13473   rtx (*gen_truncxf) (rtx, rtx);
13474
13475   rtx label = gen_label_rtx ();
13476
13477   rtx op1 = gen_reg_rtx (XFmode);
13478   rtx op2 = gen_reg_rtx (XFmode);
13479
13480   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13481   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13482
13483   emit_label (label);
13484   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13485   ix86_emit_fp_unordered_jump (label);
13486   LABEL_NUSES (label) = 1;
13487
13488   /* Truncate the result properly for strict SSE math.  */
13489   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13490       && !TARGET_MIX_SSE_I387)
13491     gen_truncxf = gen_truncxf<mode>2;
13492   else
13493     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13494
13495   emit_insn (gen_truncxf (operands[0], op1));
13496   DONE;
13497 })
13498
13499 (define_insn "fprem1xf4_i387"
13500   [(set (match_operand:XF 0 "register_operand" "=f")
13501         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13502                     (match_operand:XF 3 "register_operand" "1")]
13503                    UNSPEC_FPREM1_F))
13504    (set (match_operand:XF 1 "register_operand" "=u")
13505         (unspec:XF [(match_dup 2) (match_dup 3)]
13506                    UNSPEC_FPREM1_U))
13507    (set (reg:CCFP FPSR_REG)
13508         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13509                      UNSPEC_C2_FLAG))]
13510   "TARGET_USE_FANCY_MATH_387"
13511   "fprem1"
13512   [(set_attr "type" "fpspc")
13513    (set_attr "mode" "XF")])
13514
13515 (define_expand "remainderxf3"
13516   [(use (match_operand:XF 0 "register_operand" ""))
13517    (use (match_operand:XF 1 "general_operand" ""))
13518    (use (match_operand:XF 2 "general_operand" ""))]
13519   "TARGET_USE_FANCY_MATH_387"
13520 {
13521   rtx label = gen_label_rtx ();
13522
13523   rtx op1 = gen_reg_rtx (XFmode);
13524   rtx op2 = gen_reg_rtx (XFmode);
13525
13526   emit_move_insn (op2, operands[2]);
13527   emit_move_insn (op1, operands[1]);
13528
13529   emit_label (label);
13530   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13531   ix86_emit_fp_unordered_jump (label);
13532   LABEL_NUSES (label) = 1;
13533
13534   emit_move_insn (operands[0], op1);
13535   DONE;
13536 })
13537
13538 (define_expand "remainder<mode>3"
13539   [(use (match_operand:MODEF 0 "register_operand" ""))
13540    (use (match_operand:MODEF 1 "general_operand" ""))
13541    (use (match_operand:MODEF 2 "general_operand" ""))]
13542   "TARGET_USE_FANCY_MATH_387"
13543 {
13544   rtx (*gen_truncxf) (rtx, rtx);
13545
13546   rtx label = gen_label_rtx ();
13547
13548   rtx op1 = gen_reg_rtx (XFmode);
13549   rtx op2 = gen_reg_rtx (XFmode);
13550
13551   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13552   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13553
13554   emit_label (label);
13555
13556   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13557   ix86_emit_fp_unordered_jump (label);
13558   LABEL_NUSES (label) = 1;
13559
13560   /* Truncate the result properly for strict SSE math.  */
13561   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13562       && !TARGET_MIX_SSE_I387)
13563     gen_truncxf = gen_truncxf<mode>2;
13564   else
13565     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13566
13567   emit_insn (gen_truncxf (operands[0], op1));
13568   DONE;
13569 })
13570
13571 (define_insn "*sinxf2_i387"
13572   [(set (match_operand:XF 0 "register_operand" "=f")
13573         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
13574   "TARGET_USE_FANCY_MATH_387
13575    && flag_unsafe_math_optimizations"
13576   "fsin"
13577   [(set_attr "type" "fpspc")
13578    (set_attr "mode" "XF")])
13579
13580 (define_insn "*sin_extend<mode>xf2_i387"
13581   [(set (match_operand:XF 0 "register_operand" "=f")
13582         (unspec:XF [(float_extend:XF
13583                       (match_operand:MODEF 1 "register_operand" "0"))]
13584                    UNSPEC_SIN))]
13585   "TARGET_USE_FANCY_MATH_387
13586    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13587        || TARGET_MIX_SSE_I387)
13588    && flag_unsafe_math_optimizations"
13589   "fsin"
13590   [(set_attr "type" "fpspc")
13591    (set_attr "mode" "XF")])
13592
13593 (define_insn "*cosxf2_i387"
13594   [(set (match_operand:XF 0 "register_operand" "=f")
13595         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
13596   "TARGET_USE_FANCY_MATH_387
13597    && flag_unsafe_math_optimizations"
13598   "fcos"
13599   [(set_attr "type" "fpspc")
13600    (set_attr "mode" "XF")])
13601
13602 (define_insn "*cos_extend<mode>xf2_i387"
13603   [(set (match_operand:XF 0 "register_operand" "=f")
13604         (unspec:XF [(float_extend:XF
13605                       (match_operand:MODEF 1 "register_operand" "0"))]
13606                    UNSPEC_COS))]
13607   "TARGET_USE_FANCY_MATH_387
13608    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13609        || TARGET_MIX_SSE_I387)
13610    && flag_unsafe_math_optimizations"
13611   "fcos"
13612   [(set_attr "type" "fpspc")
13613    (set_attr "mode" "XF")])
13614
13615 ;; When sincos pattern is defined, sin and cos builtin functions will be
13616 ;; expanded to sincos pattern with one of its outputs left unused.
13617 ;; CSE pass will figure out if two sincos patterns can be combined,
13618 ;; otherwise sincos pattern will be split back to sin or cos pattern,
13619 ;; depending on the unused output.
13620
13621 (define_insn "sincosxf3"
13622   [(set (match_operand:XF 0 "register_operand" "=f")
13623         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13624                    UNSPEC_SINCOS_COS))
13625    (set (match_operand:XF 1 "register_operand" "=u")
13626         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13627   "TARGET_USE_FANCY_MATH_387
13628    && flag_unsafe_math_optimizations"
13629   "fsincos"
13630   [(set_attr "type" "fpspc")
13631    (set_attr "mode" "XF")])
13632
13633 (define_split
13634   [(set (match_operand:XF 0 "register_operand" "")
13635         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13636                    UNSPEC_SINCOS_COS))
13637    (set (match_operand:XF 1 "register_operand" "")
13638         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13639   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
13640    && can_create_pseudo_p ()"
13641   [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))])
13642
13643 (define_split
13644   [(set (match_operand:XF 0 "register_operand" "")
13645         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13646                    UNSPEC_SINCOS_COS))
13647    (set (match_operand:XF 1 "register_operand" "")
13648         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13649   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13650    && can_create_pseudo_p ()"
13651   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))])
13652
13653 (define_insn "sincos_extend<mode>xf3_i387"
13654   [(set (match_operand:XF 0 "register_operand" "=f")
13655         (unspec:XF [(float_extend:XF
13656                       (match_operand:MODEF 2 "register_operand" "0"))]
13657                    UNSPEC_SINCOS_COS))
13658    (set (match_operand:XF 1 "register_operand" "=u")
13659         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13660   "TARGET_USE_FANCY_MATH_387
13661    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13662        || TARGET_MIX_SSE_I387)
13663    && flag_unsafe_math_optimizations"
13664   "fsincos"
13665   [(set_attr "type" "fpspc")
13666    (set_attr "mode" "XF")])
13667
13668 (define_split
13669   [(set (match_operand:XF 0 "register_operand" "")
13670         (unspec:XF [(float_extend:XF
13671                       (match_operand:MODEF 2 "register_operand" ""))]
13672                    UNSPEC_SINCOS_COS))
13673    (set (match_operand:XF 1 "register_operand" "")
13674         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13675   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
13676    && can_create_pseudo_p ()"
13677   [(set (match_dup 1)
13678         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))])
13679
13680 (define_split
13681   [(set (match_operand:XF 0 "register_operand" "")
13682         (unspec:XF [(float_extend:XF
13683                       (match_operand:MODEF 2 "register_operand" ""))]
13684                    UNSPEC_SINCOS_COS))
13685    (set (match_operand:XF 1 "register_operand" "")
13686         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13687   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13688    && can_create_pseudo_p ()"
13689   [(set (match_dup 0)
13690         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))])
13691
13692 (define_expand "sincos<mode>3"
13693   [(use (match_operand:MODEF 0 "register_operand" ""))
13694    (use (match_operand:MODEF 1 "register_operand" ""))
13695    (use (match_operand:MODEF 2 "register_operand" ""))]
13696   "TARGET_USE_FANCY_MATH_387
13697    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13698        || TARGET_MIX_SSE_I387)
13699    && flag_unsafe_math_optimizations"
13700 {
13701   rtx op0 = gen_reg_rtx (XFmode);
13702   rtx op1 = gen_reg_rtx (XFmode);
13703
13704   emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
13705   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13706   emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
13707   DONE;
13708 })
13709
13710 (define_insn "fptanxf4_i387"
13711   [(set (match_operand:XF 0 "register_operand" "=f")
13712         (match_operand:XF 3 "const_double_operand" "F"))
13713    (set (match_operand:XF 1 "register_operand" "=u")
13714         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13715                    UNSPEC_TAN))]
13716   "TARGET_USE_FANCY_MATH_387
13717    && flag_unsafe_math_optimizations
13718    && standard_80387_constant_p (operands[3]) == 2"
13719   "fptan"
13720   [(set_attr "type" "fpspc")
13721    (set_attr "mode" "XF")])
13722
13723 (define_insn "fptan_extend<mode>xf4_i387"
13724   [(set (match_operand:MODEF 0 "register_operand" "=f")
13725         (match_operand:MODEF 3 "const_double_operand" "F"))
13726    (set (match_operand:XF 1 "register_operand" "=u")
13727         (unspec:XF [(float_extend:XF
13728                       (match_operand:MODEF 2 "register_operand" "0"))]
13729                    UNSPEC_TAN))]
13730   "TARGET_USE_FANCY_MATH_387
13731    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13732        || TARGET_MIX_SSE_I387)
13733    && flag_unsafe_math_optimizations
13734    && standard_80387_constant_p (operands[3]) == 2"
13735   "fptan"
13736   [(set_attr "type" "fpspc")
13737    (set_attr "mode" "XF")])
13738
13739 (define_expand "tanxf2"
13740   [(use (match_operand:XF 0 "register_operand" ""))
13741    (use (match_operand:XF 1 "register_operand" ""))]
13742   "TARGET_USE_FANCY_MATH_387
13743    && flag_unsafe_math_optimizations"
13744 {
13745   rtx one = gen_reg_rtx (XFmode);
13746   rtx op2 = CONST1_RTX (XFmode); /* fld1 */
13747
13748   emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
13749   DONE;
13750 })
13751
13752 (define_expand "tan<mode>2"
13753   [(use (match_operand:MODEF 0 "register_operand" ""))
13754    (use (match_operand:MODEF 1 "register_operand" ""))]
13755   "TARGET_USE_FANCY_MATH_387
13756    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13757        || TARGET_MIX_SSE_I387)
13758    && flag_unsafe_math_optimizations"
13759 {
13760   rtx op0 = gen_reg_rtx (XFmode);
13761
13762   rtx one = gen_reg_rtx (<MODE>mode);
13763   rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
13764
13765   emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
13766                                              operands[1], op2));
13767   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13768   DONE;
13769 })
13770
13771 (define_insn "*fpatanxf3_i387"
13772   [(set (match_operand:XF 0 "register_operand" "=f")
13773         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13774                     (match_operand:XF 2 "register_operand" "u")]
13775                    UNSPEC_FPATAN))
13776    (clobber (match_scratch:XF 3 "=2"))]
13777   "TARGET_USE_FANCY_MATH_387
13778    && flag_unsafe_math_optimizations"
13779   "fpatan"
13780   [(set_attr "type" "fpspc")
13781    (set_attr "mode" "XF")])
13782
13783 (define_insn "fpatan_extend<mode>xf3_i387"
13784   [(set (match_operand:XF 0 "register_operand" "=f")
13785         (unspec:XF [(float_extend:XF
13786                       (match_operand:MODEF 1 "register_operand" "0"))
13787                     (float_extend:XF
13788                       (match_operand:MODEF 2 "register_operand" "u"))]
13789                    UNSPEC_FPATAN))
13790    (clobber (match_scratch:XF 3 "=2"))]
13791   "TARGET_USE_FANCY_MATH_387
13792    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13793        || TARGET_MIX_SSE_I387)
13794    && flag_unsafe_math_optimizations"
13795   "fpatan"
13796   [(set_attr "type" "fpspc")
13797    (set_attr "mode" "XF")])
13798
13799 (define_expand "atan2xf3"
13800   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13801                    (unspec:XF [(match_operand:XF 2 "register_operand" "")
13802                                (match_operand:XF 1 "register_operand" "")]
13803                               UNSPEC_FPATAN))
13804               (clobber (match_scratch:XF 3 ""))])]
13805   "TARGET_USE_FANCY_MATH_387
13806    && flag_unsafe_math_optimizations")
13807
13808 (define_expand "atan2<mode>3"
13809   [(use (match_operand:MODEF 0 "register_operand" ""))
13810    (use (match_operand:MODEF 1 "register_operand" ""))
13811    (use (match_operand:MODEF 2 "register_operand" ""))]
13812   "TARGET_USE_FANCY_MATH_387
13813    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13814        || TARGET_MIX_SSE_I387)
13815    && flag_unsafe_math_optimizations"
13816 {
13817   rtx op0 = gen_reg_rtx (XFmode);
13818
13819   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
13820   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13821   DONE;
13822 })
13823
13824 (define_expand "atanxf2"
13825   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13826                    (unspec:XF [(match_dup 2)
13827                                (match_operand:XF 1 "register_operand" "")]
13828                               UNSPEC_FPATAN))
13829               (clobber (match_scratch:XF 3 ""))])]
13830   "TARGET_USE_FANCY_MATH_387
13831    && flag_unsafe_math_optimizations"
13832 {
13833   operands[2] = gen_reg_rtx (XFmode);
13834   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
13835 })
13836
13837 (define_expand "atan<mode>2"
13838   [(use (match_operand:MODEF 0 "register_operand" ""))
13839    (use (match_operand:MODEF 1 "register_operand" ""))]
13840   "TARGET_USE_FANCY_MATH_387
13841    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13842        || TARGET_MIX_SSE_I387)
13843    && flag_unsafe_math_optimizations"
13844 {
13845   rtx op0 = gen_reg_rtx (XFmode);
13846
13847   rtx op2 = gen_reg_rtx (<MODE>mode);
13848   emit_move_insn (op2, CONST1_RTX (<MODE>mode));  /* fld1 */
13849
13850   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
13851   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13852   DONE;
13853 })
13854
13855 (define_expand "asinxf2"
13856   [(set (match_dup 2)
13857         (mult:XF (match_operand:XF 1 "register_operand" "")
13858                  (match_dup 1)))
13859    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13860    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13861    (parallel [(set (match_operand:XF 0 "register_operand" "")
13862                    (unspec:XF [(match_dup 5) (match_dup 1)]
13863                               UNSPEC_FPATAN))
13864               (clobber (match_scratch:XF 6 ""))])]
13865   "TARGET_USE_FANCY_MATH_387
13866    && flag_unsafe_math_optimizations"
13867 {
13868   int i;
13869
13870   if (optimize_insn_for_size_p ())
13871     FAIL;
13872
13873   for (i = 2; i < 6; i++)
13874     operands[i] = gen_reg_rtx (XFmode);
13875
13876   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13877 })
13878
13879 (define_expand "asin<mode>2"
13880   [(use (match_operand:MODEF 0 "register_operand" ""))
13881    (use (match_operand:MODEF 1 "general_operand" ""))]
13882  "TARGET_USE_FANCY_MATH_387
13883    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13884        || TARGET_MIX_SSE_I387)
13885    && flag_unsafe_math_optimizations"
13886 {
13887   rtx op0 = gen_reg_rtx (XFmode);
13888   rtx op1 = gen_reg_rtx (XFmode);
13889
13890   if (optimize_insn_for_size_p ())
13891     FAIL;
13892
13893   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13894   emit_insn (gen_asinxf2 (op0, op1));
13895   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13896   DONE;
13897 })
13898
13899 (define_expand "acosxf2"
13900   [(set (match_dup 2)
13901         (mult:XF (match_operand:XF 1 "register_operand" "")
13902                  (match_dup 1)))
13903    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13904    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13905    (parallel [(set (match_operand:XF 0 "register_operand" "")
13906                    (unspec:XF [(match_dup 1) (match_dup 5)]
13907                               UNSPEC_FPATAN))
13908               (clobber (match_scratch:XF 6 ""))])]
13909   "TARGET_USE_FANCY_MATH_387
13910    && flag_unsafe_math_optimizations"
13911 {
13912   int i;
13913
13914   if (optimize_insn_for_size_p ())
13915     FAIL;
13916
13917   for (i = 2; i < 6; i++)
13918     operands[i] = gen_reg_rtx (XFmode);
13919
13920   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13921 })
13922
13923 (define_expand "acos<mode>2"
13924   [(use (match_operand:MODEF 0 "register_operand" ""))
13925    (use (match_operand:MODEF 1 "general_operand" ""))]
13926  "TARGET_USE_FANCY_MATH_387
13927    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13928        || TARGET_MIX_SSE_I387)
13929    && flag_unsafe_math_optimizations"
13930 {
13931   rtx op0 = gen_reg_rtx (XFmode);
13932   rtx op1 = gen_reg_rtx (XFmode);
13933
13934   if (optimize_insn_for_size_p ())
13935     FAIL;
13936
13937   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13938   emit_insn (gen_acosxf2 (op0, op1));
13939   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13940   DONE;
13941 })
13942
13943 (define_insn "fyl2xxf3_i387"
13944   [(set (match_operand:XF 0 "register_operand" "=f")
13945         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13946                     (match_operand:XF 2 "register_operand" "u")]
13947                    UNSPEC_FYL2X))
13948    (clobber (match_scratch:XF 3 "=2"))]
13949   "TARGET_USE_FANCY_MATH_387
13950    && flag_unsafe_math_optimizations"
13951   "fyl2x"
13952   [(set_attr "type" "fpspc")
13953    (set_attr "mode" "XF")])
13954
13955 (define_insn "fyl2x_extend<mode>xf3_i387"
13956   [(set (match_operand:XF 0 "register_operand" "=f")
13957         (unspec:XF [(float_extend:XF
13958                       (match_operand:MODEF 1 "register_operand" "0"))
13959                     (match_operand:XF 2 "register_operand" "u")]
13960                    UNSPEC_FYL2X))
13961    (clobber (match_scratch:XF 3 "=2"))]
13962   "TARGET_USE_FANCY_MATH_387
13963    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13964        || TARGET_MIX_SSE_I387)
13965    && flag_unsafe_math_optimizations"
13966   "fyl2x"
13967   [(set_attr "type" "fpspc")
13968    (set_attr "mode" "XF")])
13969
13970 (define_expand "logxf2"
13971   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13972                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
13973                                (match_dup 2)] UNSPEC_FYL2X))
13974               (clobber (match_scratch:XF 3 ""))])]
13975   "TARGET_USE_FANCY_MATH_387
13976    && flag_unsafe_math_optimizations"
13977 {
13978   operands[2] = gen_reg_rtx (XFmode);
13979   emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
13980 })
13981
13982 (define_expand "log<mode>2"
13983   [(use (match_operand:MODEF 0 "register_operand" ""))
13984    (use (match_operand:MODEF 1 "register_operand" ""))]
13985   "TARGET_USE_FANCY_MATH_387
13986    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13987        || TARGET_MIX_SSE_I387)
13988    && flag_unsafe_math_optimizations"
13989 {
13990   rtx op0 = gen_reg_rtx (XFmode);
13991
13992   rtx op2 = gen_reg_rtx (XFmode);
13993   emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
13994
13995   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
13996   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13997   DONE;
13998 })
13999
14000 (define_expand "log10xf2"
14001   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14002                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14003                                (match_dup 2)] UNSPEC_FYL2X))
14004               (clobber (match_scratch:XF 3 ""))])]
14005   "TARGET_USE_FANCY_MATH_387
14006    && flag_unsafe_math_optimizations"
14007 {
14008   operands[2] = gen_reg_rtx (XFmode);
14009   emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
14010 })
14011
14012 (define_expand "log10<mode>2"
14013   [(use (match_operand:MODEF 0 "register_operand" ""))
14014    (use (match_operand:MODEF 1 "register_operand" ""))]
14015   "TARGET_USE_FANCY_MATH_387
14016    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14017        || TARGET_MIX_SSE_I387)
14018    && flag_unsafe_math_optimizations"
14019 {
14020   rtx op0 = gen_reg_rtx (XFmode);
14021
14022   rtx op2 = gen_reg_rtx (XFmode);
14023   emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
14024
14025   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14026   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14027   DONE;
14028 })
14029
14030 (define_expand "log2xf2"
14031   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14032                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14033                                (match_dup 2)] UNSPEC_FYL2X))
14034               (clobber (match_scratch:XF 3 ""))])]
14035   "TARGET_USE_FANCY_MATH_387
14036    && flag_unsafe_math_optimizations"
14037 {
14038   operands[2] = gen_reg_rtx (XFmode);
14039   emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
14040 })
14041
14042 (define_expand "log2<mode>2"
14043   [(use (match_operand:MODEF 0 "register_operand" ""))
14044    (use (match_operand:MODEF 1 "register_operand" ""))]
14045   "TARGET_USE_FANCY_MATH_387
14046    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14047        || TARGET_MIX_SSE_I387)
14048    && flag_unsafe_math_optimizations"
14049 {
14050   rtx op0 = gen_reg_rtx (XFmode);
14051
14052   rtx op2 = gen_reg_rtx (XFmode);
14053   emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
14054
14055   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14056   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14057   DONE;
14058 })
14059
14060 (define_insn "fyl2xp1xf3_i387"
14061   [(set (match_operand:XF 0 "register_operand" "=f")
14062         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
14063                     (match_operand:XF 2 "register_operand" "u")]
14064                    UNSPEC_FYL2XP1))
14065    (clobber (match_scratch:XF 3 "=2"))]
14066   "TARGET_USE_FANCY_MATH_387
14067    && flag_unsafe_math_optimizations"
14068   "fyl2xp1"
14069   [(set_attr "type" "fpspc")
14070    (set_attr "mode" "XF")])
14071
14072 (define_insn "fyl2xp1_extend<mode>xf3_i387"
14073   [(set (match_operand:XF 0 "register_operand" "=f")
14074         (unspec:XF [(float_extend:XF
14075                       (match_operand:MODEF 1 "register_operand" "0"))
14076                     (match_operand:XF 2 "register_operand" "u")]
14077                    UNSPEC_FYL2XP1))
14078    (clobber (match_scratch:XF 3 "=2"))]
14079   "TARGET_USE_FANCY_MATH_387
14080    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14081        || TARGET_MIX_SSE_I387)
14082    && flag_unsafe_math_optimizations"
14083   "fyl2xp1"
14084   [(set_attr "type" "fpspc")
14085    (set_attr "mode" "XF")])
14086
14087 (define_expand "log1pxf2"
14088   [(use (match_operand:XF 0 "register_operand" ""))
14089    (use (match_operand:XF 1 "register_operand" ""))]
14090   "TARGET_USE_FANCY_MATH_387
14091    && flag_unsafe_math_optimizations"
14092 {
14093   if (optimize_insn_for_size_p ())
14094     FAIL;
14095
14096   ix86_emit_i387_log1p (operands[0], operands[1]);
14097   DONE;
14098 })
14099
14100 (define_expand "log1p<mode>2"
14101   [(use (match_operand:MODEF 0 "register_operand" ""))
14102    (use (match_operand:MODEF 1 "register_operand" ""))]
14103   "TARGET_USE_FANCY_MATH_387
14104    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14105        || TARGET_MIX_SSE_I387)
14106    && flag_unsafe_math_optimizations"
14107 {
14108   rtx op0;
14109
14110   if (optimize_insn_for_size_p ())
14111     FAIL;
14112
14113   op0 = gen_reg_rtx (XFmode);
14114
14115   operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
14116
14117   ix86_emit_i387_log1p (op0, operands[1]);
14118   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14119   DONE;
14120 })
14121
14122 (define_insn "fxtractxf3_i387"
14123   [(set (match_operand:XF 0 "register_operand" "=f")
14124         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
14125                    UNSPEC_XTRACT_FRACT))
14126    (set (match_operand:XF 1 "register_operand" "=u")
14127         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
14128   "TARGET_USE_FANCY_MATH_387
14129    && flag_unsafe_math_optimizations"
14130   "fxtract"
14131   [(set_attr "type" "fpspc")
14132    (set_attr "mode" "XF")])
14133
14134 (define_insn "fxtract_extend<mode>xf3_i387"
14135   [(set (match_operand:XF 0 "register_operand" "=f")
14136         (unspec:XF [(float_extend:XF
14137                       (match_operand:MODEF 2 "register_operand" "0"))]
14138                    UNSPEC_XTRACT_FRACT))
14139    (set (match_operand:XF 1 "register_operand" "=u")
14140         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
14141   "TARGET_USE_FANCY_MATH_387
14142    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14143        || TARGET_MIX_SSE_I387)
14144    && flag_unsafe_math_optimizations"
14145   "fxtract"
14146   [(set_attr "type" "fpspc")
14147    (set_attr "mode" "XF")])
14148
14149 (define_expand "logbxf2"
14150   [(parallel [(set (match_dup 2)
14151                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14152                               UNSPEC_XTRACT_FRACT))
14153               (set (match_operand:XF 0 "register_operand" "")
14154                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14155   "TARGET_USE_FANCY_MATH_387
14156    && flag_unsafe_math_optimizations"
14157   "operands[2] = gen_reg_rtx (XFmode);")
14158
14159 (define_expand "logb<mode>2"
14160   [(use (match_operand:MODEF 0 "register_operand" ""))
14161    (use (match_operand:MODEF 1 "register_operand" ""))]
14162   "TARGET_USE_FANCY_MATH_387
14163    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14164        || TARGET_MIX_SSE_I387)
14165    && flag_unsafe_math_optimizations"
14166 {
14167   rtx op0 = gen_reg_rtx (XFmode);
14168   rtx op1 = gen_reg_rtx (XFmode);
14169
14170   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14171   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
14172   DONE;
14173 })
14174
14175 (define_expand "ilogbxf2"
14176   [(use (match_operand:SI 0 "register_operand" ""))
14177    (use (match_operand:XF 1 "register_operand" ""))]
14178   "TARGET_USE_FANCY_MATH_387
14179    && flag_unsafe_math_optimizations"
14180 {
14181   rtx op0, op1;
14182
14183   if (optimize_insn_for_size_p ())
14184     FAIL;
14185
14186   op0 = gen_reg_rtx (XFmode);
14187   op1 = gen_reg_rtx (XFmode);
14188
14189   emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
14190   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14191   DONE;
14192 })
14193
14194 (define_expand "ilogb<mode>2"
14195   [(use (match_operand:SI 0 "register_operand" ""))
14196    (use (match_operand:MODEF 1 "register_operand" ""))]
14197   "TARGET_USE_FANCY_MATH_387
14198    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14199        || TARGET_MIX_SSE_I387)
14200    && flag_unsafe_math_optimizations"
14201 {
14202   rtx op0, op1;
14203
14204   if (optimize_insn_for_size_p ())
14205     FAIL;
14206
14207   op0 = gen_reg_rtx (XFmode);
14208   op1 = gen_reg_rtx (XFmode);
14209
14210   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14211   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14212   DONE;
14213 })
14214
14215 (define_insn "*f2xm1xf2_i387"
14216   [(set (match_operand:XF 0 "register_operand" "=f")
14217         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14218                    UNSPEC_F2XM1))]
14219   "TARGET_USE_FANCY_MATH_387
14220    && flag_unsafe_math_optimizations"
14221   "f2xm1"
14222   [(set_attr "type" "fpspc")
14223    (set_attr "mode" "XF")])
14224
14225 (define_insn "*fscalexf4_i387"
14226   [(set (match_operand:XF 0 "register_operand" "=f")
14227         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14228                     (match_operand:XF 3 "register_operand" "1")]
14229                    UNSPEC_FSCALE_FRACT))
14230    (set (match_operand:XF 1 "register_operand" "=u")
14231         (unspec:XF [(match_dup 2) (match_dup 3)]
14232                    UNSPEC_FSCALE_EXP))]
14233   "TARGET_USE_FANCY_MATH_387
14234    && flag_unsafe_math_optimizations"
14235   "fscale"
14236   [(set_attr "type" "fpspc")
14237    (set_attr "mode" "XF")])
14238
14239 (define_expand "expNcorexf3"
14240   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14241                                (match_operand:XF 2 "register_operand" "")))
14242    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14243    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14244    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14245    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
14246    (parallel [(set (match_operand:XF 0 "register_operand" "")
14247                    (unspec:XF [(match_dup 8) (match_dup 4)]
14248                               UNSPEC_FSCALE_FRACT))
14249               (set (match_dup 9)
14250                    (unspec:XF [(match_dup 8) (match_dup 4)]
14251                               UNSPEC_FSCALE_EXP))])]
14252   "TARGET_USE_FANCY_MATH_387
14253    && flag_unsafe_math_optimizations"
14254 {
14255   int i;
14256
14257   if (optimize_insn_for_size_p ())
14258     FAIL;
14259
14260   for (i = 3; i < 10; i++)
14261     operands[i] = gen_reg_rtx (XFmode);
14262
14263   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
14264 })
14265
14266 (define_expand "expxf2"
14267   [(use (match_operand:XF 0 "register_operand" ""))
14268    (use (match_operand:XF 1 "register_operand" ""))]
14269   "TARGET_USE_FANCY_MATH_387
14270    && flag_unsafe_math_optimizations"
14271 {
14272   rtx op2;
14273
14274   if (optimize_insn_for_size_p ())
14275     FAIL;
14276
14277   op2 = gen_reg_rtx (XFmode);
14278   emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
14279
14280   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14281   DONE;
14282 })
14283
14284 (define_expand "exp<mode>2"
14285   [(use (match_operand:MODEF 0 "register_operand" ""))
14286    (use (match_operand:MODEF 1 "general_operand" ""))]
14287  "TARGET_USE_FANCY_MATH_387
14288    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14289        || TARGET_MIX_SSE_I387)
14290    && flag_unsafe_math_optimizations"
14291 {
14292   rtx op0, op1;
14293
14294   if (optimize_insn_for_size_p ())
14295     FAIL;
14296
14297   op0 = gen_reg_rtx (XFmode);
14298   op1 = gen_reg_rtx (XFmode);
14299
14300   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14301   emit_insn (gen_expxf2 (op0, op1));
14302   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14303   DONE;
14304 })
14305
14306 (define_expand "exp10xf2"
14307   [(use (match_operand:XF 0 "register_operand" ""))
14308    (use (match_operand:XF 1 "register_operand" ""))]
14309   "TARGET_USE_FANCY_MATH_387
14310    && flag_unsafe_math_optimizations"
14311 {
14312   rtx op2;
14313
14314   if (optimize_insn_for_size_p ())
14315     FAIL;
14316
14317   op2 = gen_reg_rtx (XFmode);
14318   emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
14319
14320   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14321   DONE;
14322 })
14323
14324 (define_expand "exp10<mode>2"
14325   [(use (match_operand:MODEF 0 "register_operand" ""))
14326    (use (match_operand:MODEF 1 "general_operand" ""))]
14327  "TARGET_USE_FANCY_MATH_387
14328    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14329        || TARGET_MIX_SSE_I387)
14330    && flag_unsafe_math_optimizations"
14331 {
14332   rtx op0, op1;
14333
14334   if (optimize_insn_for_size_p ())
14335     FAIL;
14336
14337   op0 = gen_reg_rtx (XFmode);
14338   op1 = gen_reg_rtx (XFmode);
14339
14340   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14341   emit_insn (gen_exp10xf2 (op0, op1));
14342   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14343   DONE;
14344 })
14345
14346 (define_expand "exp2xf2"
14347   [(use (match_operand:XF 0 "register_operand" ""))
14348    (use (match_operand:XF 1 "register_operand" ""))]
14349   "TARGET_USE_FANCY_MATH_387
14350    && flag_unsafe_math_optimizations"
14351 {
14352   rtx op2;
14353
14354   if (optimize_insn_for_size_p ())
14355     FAIL;
14356
14357   op2 = gen_reg_rtx (XFmode);
14358   emit_move_insn (op2, CONST1_RTX (XFmode));  /* fld1 */
14359
14360   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14361   DONE;
14362 })
14363
14364 (define_expand "exp2<mode>2"
14365   [(use (match_operand:MODEF 0 "register_operand" ""))
14366    (use (match_operand:MODEF 1 "general_operand" ""))]
14367  "TARGET_USE_FANCY_MATH_387
14368    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14369        || TARGET_MIX_SSE_I387)
14370    && flag_unsafe_math_optimizations"
14371 {
14372   rtx op0, op1;
14373
14374   if (optimize_insn_for_size_p ())
14375     FAIL;
14376
14377   op0 = gen_reg_rtx (XFmode);
14378   op1 = gen_reg_rtx (XFmode);
14379
14380   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14381   emit_insn (gen_exp2xf2 (op0, op1));
14382   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14383   DONE;
14384 })
14385
14386 (define_expand "expm1xf2"
14387   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14388                                (match_dup 2)))
14389    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14390    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14391    (set (match_dup 9) (float_extend:XF (match_dup 13)))
14392    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14393    (parallel [(set (match_dup 7)
14394                    (unspec:XF [(match_dup 6) (match_dup 4)]
14395                               UNSPEC_FSCALE_FRACT))
14396               (set (match_dup 8)
14397                    (unspec:XF [(match_dup 6) (match_dup 4)]
14398                               UNSPEC_FSCALE_EXP))])
14399    (parallel [(set (match_dup 10)
14400                    (unspec:XF [(match_dup 9) (match_dup 8)]
14401                               UNSPEC_FSCALE_FRACT))
14402               (set (match_dup 11)
14403                    (unspec:XF [(match_dup 9) (match_dup 8)]
14404                               UNSPEC_FSCALE_EXP))])
14405    (set (match_dup 12) (minus:XF (match_dup 10)
14406                                  (float_extend:XF (match_dup 13))))
14407    (set (match_operand:XF 0 "register_operand" "")
14408         (plus:XF (match_dup 12) (match_dup 7)))]
14409   "TARGET_USE_FANCY_MATH_387
14410    && flag_unsafe_math_optimizations"
14411 {
14412   int i;
14413
14414   if (optimize_insn_for_size_p ())
14415     FAIL;
14416
14417   for (i = 2; i < 13; i++)
14418     operands[i] = gen_reg_rtx (XFmode);
14419
14420   operands[13]
14421     = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
14422
14423   emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
14424 })
14425
14426 (define_expand "expm1<mode>2"
14427   [(use (match_operand:MODEF 0 "register_operand" ""))
14428    (use (match_operand:MODEF 1 "general_operand" ""))]
14429  "TARGET_USE_FANCY_MATH_387
14430    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14431        || TARGET_MIX_SSE_I387)
14432    && flag_unsafe_math_optimizations"
14433 {
14434   rtx op0, op1;
14435
14436   if (optimize_insn_for_size_p ())
14437     FAIL;
14438
14439   op0 = gen_reg_rtx (XFmode);
14440   op1 = gen_reg_rtx (XFmode);
14441
14442   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14443   emit_insn (gen_expm1xf2 (op0, op1));
14444   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14445   DONE;
14446 })
14447
14448 (define_expand "ldexpxf3"
14449   [(set (match_dup 3)
14450         (float:XF (match_operand:SI 2 "register_operand" "")))
14451    (parallel [(set (match_operand:XF 0 " register_operand" "")
14452                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14453                                (match_dup 3)]
14454                               UNSPEC_FSCALE_FRACT))
14455               (set (match_dup 4)
14456                    (unspec:XF [(match_dup 1) (match_dup 3)]
14457                               UNSPEC_FSCALE_EXP))])]
14458   "TARGET_USE_FANCY_MATH_387
14459    && flag_unsafe_math_optimizations"
14460 {
14461   if (optimize_insn_for_size_p ())
14462     FAIL;
14463
14464   operands[3] = gen_reg_rtx (XFmode);
14465   operands[4] = gen_reg_rtx (XFmode);
14466 })
14467
14468 (define_expand "ldexp<mode>3"
14469   [(use (match_operand:MODEF 0 "register_operand" ""))
14470    (use (match_operand:MODEF 1 "general_operand" ""))
14471    (use (match_operand:SI 2 "register_operand" ""))]
14472  "TARGET_USE_FANCY_MATH_387
14473    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14474        || TARGET_MIX_SSE_I387)
14475    && flag_unsafe_math_optimizations"
14476 {
14477   rtx op0, op1;
14478
14479   if (optimize_insn_for_size_p ())
14480     FAIL;
14481
14482   op0 = gen_reg_rtx (XFmode);
14483   op1 = gen_reg_rtx (XFmode);
14484
14485   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14486   emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
14487   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14488   DONE;
14489 })
14490
14491 (define_expand "scalbxf3"
14492   [(parallel [(set (match_operand:XF 0 " register_operand" "")
14493                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14494                                (match_operand:XF 2 "register_operand" "")]
14495                               UNSPEC_FSCALE_FRACT))
14496               (set (match_dup 3)
14497                    (unspec:XF [(match_dup 1) (match_dup 2)]
14498                               UNSPEC_FSCALE_EXP))])]
14499   "TARGET_USE_FANCY_MATH_387
14500    && flag_unsafe_math_optimizations"
14501 {
14502   if (optimize_insn_for_size_p ())
14503     FAIL;
14504
14505   operands[3] = gen_reg_rtx (XFmode);
14506 })
14507
14508 (define_expand "scalb<mode>3"
14509   [(use (match_operand:MODEF 0 "register_operand" ""))
14510    (use (match_operand:MODEF 1 "general_operand" ""))
14511    (use (match_operand:MODEF 2 "general_operand" ""))]
14512  "TARGET_USE_FANCY_MATH_387
14513    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14514        || TARGET_MIX_SSE_I387)
14515    && flag_unsafe_math_optimizations"
14516 {
14517   rtx op0, op1, op2;
14518
14519   if (optimize_insn_for_size_p ())
14520     FAIL;
14521
14522   op0 = gen_reg_rtx (XFmode);
14523   op1 = gen_reg_rtx (XFmode);
14524   op2 = gen_reg_rtx (XFmode);
14525
14526   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14527   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
14528   emit_insn (gen_scalbxf3 (op0, op1, op2));
14529   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14530   DONE;
14531 })
14532
14533 (define_expand "significandxf2"
14534   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14535                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14536                               UNSPEC_XTRACT_FRACT))
14537               (set (match_dup 2)
14538                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14539   "TARGET_USE_FANCY_MATH_387
14540    && flag_unsafe_math_optimizations"
14541   "operands[2] = gen_reg_rtx (XFmode);")
14542
14543 (define_expand "significand<mode>2"
14544   [(use (match_operand:MODEF 0 "register_operand" ""))
14545    (use (match_operand:MODEF 1 "register_operand" ""))]
14546   "TARGET_USE_FANCY_MATH_387
14547    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14548        || TARGET_MIX_SSE_I387)
14549    && flag_unsafe_math_optimizations"
14550 {
14551   rtx op0 = gen_reg_rtx (XFmode);
14552   rtx op1 = gen_reg_rtx (XFmode);
14553
14554   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14555   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14556   DONE;
14557 })
14558 \f
14559
14560 (define_insn "sse4_1_round<mode>2"
14561   [(set (match_operand:MODEF 0 "register_operand" "=x")
14562         (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
14563                        (match_operand:SI 2 "const_0_to_15_operand" "n")]
14564                       UNSPEC_ROUND))]
14565   "TARGET_ROUND"
14566   "%vround<ssemodesuffix>\t{%2, %1, %d0|%d0, %1, %2}"
14567   [(set_attr "type" "ssecvt")
14568    (set_attr "prefix_extra" "1")
14569    (set_attr "prefix" "maybe_vex")
14570    (set_attr "mode" "<MODE>")])
14571
14572 (define_insn "rintxf2"
14573   [(set (match_operand:XF 0 "register_operand" "=f")
14574         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14575                    UNSPEC_FRNDINT))]
14576   "TARGET_USE_FANCY_MATH_387
14577    && flag_unsafe_math_optimizations"
14578   "frndint"
14579   [(set_attr "type" "fpspc")
14580    (set_attr "mode" "XF")])
14581
14582 (define_expand "rint<mode>2"
14583   [(use (match_operand:MODEF 0 "register_operand" ""))
14584    (use (match_operand:MODEF 1 "register_operand" ""))]
14585   "(TARGET_USE_FANCY_MATH_387
14586     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14587         || TARGET_MIX_SSE_I387)
14588     && flag_unsafe_math_optimizations)
14589    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14590        && !flag_trapping_math)"
14591 {
14592   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14593       && !flag_trapping_math)
14594     {
14595       if (TARGET_ROUND)
14596         emit_insn (gen_sse4_1_round<mode>2
14597                    (operands[0], operands[1], GEN_INT (ROUND_MXCSR)));
14598       else if (optimize_insn_for_size_p ())
14599         FAIL;
14600       else
14601         ix86_expand_rint (operands[0], operands[1]);
14602     }
14603   else
14604     {
14605       rtx op0 = gen_reg_rtx (XFmode);
14606       rtx op1 = gen_reg_rtx (XFmode);
14607
14608       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14609       emit_insn (gen_rintxf2 (op0, op1));
14610
14611       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14612     }
14613   DONE;
14614 })
14615
14616 (define_expand "round<mode>2"
14617   [(match_operand:X87MODEF 0 "register_operand" "")
14618    (match_operand:X87MODEF 1 "nonimmediate_operand" "")]
14619   "(TARGET_USE_FANCY_MATH_387
14620     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14621         || TARGET_MIX_SSE_I387)
14622     && flag_unsafe_math_optimizations)
14623    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14624        && !flag_trapping_math && !flag_rounding_math)"
14625 {
14626   if (optimize_insn_for_size_p ())
14627     FAIL;
14628
14629   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14630       && !flag_trapping_math && !flag_rounding_math)
14631     {
14632       if (TARGET_ROUND)
14633         {
14634           operands[1] = force_reg (<MODE>mode, operands[1]);
14635           ix86_expand_round_sse4 (operands[0], operands[1]);
14636         }
14637       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14638         ix86_expand_round (operands[0], operands[1]);
14639       else
14640         ix86_expand_rounddf_32 (operands[0], operands[1]);
14641     }
14642   else
14643     {
14644       operands[1] = force_reg (<MODE>mode, operands[1]);
14645       ix86_emit_i387_round (operands[0], operands[1]);
14646     }
14647   DONE;
14648 })
14649
14650 (define_insn_and_split "*fistdi2_1"
14651   [(set (match_operand:DI 0 "nonimmediate_operand" "")
14652         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14653                    UNSPEC_FIST))]
14654   "TARGET_USE_FANCY_MATH_387
14655    && can_create_pseudo_p ()"
14656   "#"
14657   "&& 1"
14658   [(const_int 0)]
14659 {
14660   if (memory_operand (operands[0], VOIDmode))
14661     emit_insn (gen_fistdi2 (operands[0], operands[1]));
14662   else
14663     {
14664       operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
14665       emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
14666                                          operands[2]));
14667     }
14668   DONE;
14669 }
14670   [(set_attr "type" "fpspc")
14671    (set_attr "mode" "DI")])
14672
14673 (define_insn "fistdi2"
14674   [(set (match_operand:DI 0 "memory_operand" "=m")
14675         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14676                    UNSPEC_FIST))
14677    (clobber (match_scratch:XF 2 "=&1f"))]
14678   "TARGET_USE_FANCY_MATH_387"
14679   "* return output_fix_trunc (insn, operands, false);"
14680   [(set_attr "type" "fpspc")
14681    (set_attr "mode" "DI")])
14682
14683 (define_insn "fistdi2_with_temp"
14684   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14685         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14686                    UNSPEC_FIST))
14687    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))
14688    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
14689   "TARGET_USE_FANCY_MATH_387"
14690   "#"
14691   [(set_attr "type" "fpspc")
14692    (set_attr "mode" "DI")])
14693
14694 (define_split
14695   [(set (match_operand:DI 0 "register_operand" "")
14696         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14697                    UNSPEC_FIST))
14698    (clobber (match_operand:DI 2 "memory_operand" ""))
14699    (clobber (match_scratch 3 ""))]
14700   "reload_completed"
14701   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14702               (clobber (match_dup 3))])
14703    (set (match_dup 0) (match_dup 2))])
14704
14705 (define_split
14706   [(set (match_operand:DI 0 "memory_operand" "")
14707         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14708                    UNSPEC_FIST))
14709    (clobber (match_operand:DI 2 "memory_operand" ""))
14710    (clobber (match_scratch 3 ""))]
14711   "reload_completed"
14712   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14713               (clobber (match_dup 3))])])
14714
14715 (define_insn_and_split "*fist<mode>2_1"
14716   [(set (match_operand:SWI24 0 "register_operand" "")
14717         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14718                       UNSPEC_FIST))]
14719   "TARGET_USE_FANCY_MATH_387
14720    && can_create_pseudo_p ()"
14721   "#"
14722   "&& 1"
14723   [(const_int 0)]
14724 {
14725   operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14726   emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
14727                                         operands[2]));
14728   DONE;
14729 }
14730   [(set_attr "type" "fpspc")
14731    (set_attr "mode" "<MODE>")])
14732
14733 (define_insn "fist<mode>2"
14734   [(set (match_operand:SWI24 0 "memory_operand" "=m")
14735         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14736                       UNSPEC_FIST))]
14737   "TARGET_USE_FANCY_MATH_387"
14738   "* return output_fix_trunc (insn, operands, false);"
14739   [(set_attr "type" "fpspc")
14740    (set_attr "mode" "<MODE>")])
14741
14742 (define_insn "fist<mode>2_with_temp"
14743   [(set (match_operand:SWI24 0 "register_operand" "=r")
14744         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14745                       UNSPEC_FIST))
14746    (clobber (match_operand:SWI24 2 "memory_operand" "=m"))]
14747   "TARGET_USE_FANCY_MATH_387"
14748   "#"
14749   [(set_attr "type" "fpspc")
14750    (set_attr "mode" "<MODE>")])
14751
14752 (define_split
14753   [(set (match_operand:SWI24 0 "register_operand" "")
14754         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14755                       UNSPEC_FIST))
14756    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14757   "reload_completed"
14758   [(set (match_dup 2) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))
14759    (set (match_dup 0) (match_dup 2))])
14760
14761 (define_split
14762   [(set (match_operand:SWI24 0 "memory_operand" "")
14763         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14764                       UNSPEC_FIST))
14765    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14766   "reload_completed"
14767   [(set (match_dup 0) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))])
14768
14769 (define_expand "lrintxf<mode>2"
14770   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14771      (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14772                      UNSPEC_FIST))]
14773   "TARGET_USE_FANCY_MATH_387")
14774
14775 (define_expand "lrint<MODEF:mode><SWI48x:mode>2"
14776   [(set (match_operand:SWI48x 0 "nonimmediate_operand" "")
14777      (unspec:SWI48x [(match_operand:MODEF 1 "register_operand" "")]
14778                         UNSPEC_FIX_NOTRUNC))]
14779   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
14780    && ((<SWI48x:MODE>mode != DImode) || TARGET_64BIT)")
14781
14782 (define_expand "lround<X87MODEF:mode><SWI248x:mode>2"
14783   [(match_operand:SWI248x 0 "nonimmediate_operand" "")
14784    (match_operand:X87MODEF 1 "register_operand" "")]
14785   "(TARGET_USE_FANCY_MATH_387
14786     && (!(SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
14787         || TARGET_MIX_SSE_I387)
14788     && flag_unsafe_math_optimizations)
14789    || (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14790        && <SWI248x:MODE>mode != HImode 
14791        && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14792        && !flag_trapping_math && !flag_rounding_math)"
14793 {
14794   if (optimize_insn_for_size_p ())
14795     FAIL;
14796
14797   if (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14798       && <SWI248x:MODE>mode != HImode
14799       && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14800       && !flag_trapping_math && !flag_rounding_math)
14801     ix86_expand_lround (operands[0], operands[1]);
14802   else
14803     ix86_emit_i387_round (operands[0], operands[1]);
14804   DONE;
14805 })
14806
14807 ;; Rounding mode control word calculation could clobber FLAGS_REG.
14808 (define_insn_and_split "frndintxf2_floor"
14809   [(set (match_operand:XF 0 "register_operand" "")
14810         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14811          UNSPEC_FRNDINT_FLOOR))
14812    (clobber (reg:CC FLAGS_REG))]
14813   "TARGET_USE_FANCY_MATH_387
14814    && flag_unsafe_math_optimizations
14815    && can_create_pseudo_p ()"
14816   "#"
14817   "&& 1"
14818   [(const_int 0)]
14819 {
14820   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14821
14822   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14823   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14824
14825   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
14826                                         operands[2], operands[3]));
14827   DONE;
14828 }
14829   [(set_attr "type" "frndint")
14830    (set_attr "i387_cw" "floor")
14831    (set_attr "mode" "XF")])
14832
14833 (define_insn "frndintxf2_floor_i387"
14834   [(set (match_operand:XF 0 "register_operand" "=f")
14835         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14836          UNSPEC_FRNDINT_FLOOR))
14837    (use (match_operand:HI 2 "memory_operand" "m"))
14838    (use (match_operand:HI 3 "memory_operand" "m"))]
14839   "TARGET_USE_FANCY_MATH_387
14840    && flag_unsafe_math_optimizations"
14841   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
14842   [(set_attr "type" "frndint")
14843    (set_attr "i387_cw" "floor")
14844    (set_attr "mode" "XF")])
14845
14846 (define_expand "floorxf2"
14847   [(use (match_operand:XF 0 "register_operand" ""))
14848    (use (match_operand:XF 1 "register_operand" ""))]
14849   "TARGET_USE_FANCY_MATH_387
14850    && flag_unsafe_math_optimizations"
14851 {
14852   if (optimize_insn_for_size_p ())
14853     FAIL;
14854   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
14855   DONE;
14856 })
14857
14858 (define_expand "floor<mode>2"
14859   [(use (match_operand:MODEF 0 "register_operand" ""))
14860    (use (match_operand:MODEF 1 "register_operand" ""))]
14861   "(TARGET_USE_FANCY_MATH_387
14862     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14863         || TARGET_MIX_SSE_I387)
14864     && flag_unsafe_math_optimizations)
14865    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14866        && !flag_trapping_math)"
14867 {
14868   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14869       && !flag_trapping_math)
14870     {
14871       if (TARGET_ROUND)
14872         emit_insn (gen_sse4_1_round<mode>2
14873                    (operands[0], operands[1], GEN_INT (ROUND_FLOOR)));
14874       else if (optimize_insn_for_size_p ())
14875         FAIL;
14876       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14877         ix86_expand_floorceil (operands[0], operands[1], true);
14878       else
14879         ix86_expand_floorceildf_32 (operands[0], operands[1], true);
14880     }
14881   else
14882     {
14883       rtx op0, op1;
14884
14885       if (optimize_insn_for_size_p ())
14886         FAIL;
14887
14888       op0 = gen_reg_rtx (XFmode);
14889       op1 = gen_reg_rtx (XFmode);
14890       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14891       emit_insn (gen_frndintxf2_floor (op0, op1));
14892
14893       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14894     }
14895   DONE;
14896 })
14897
14898 (define_insn_and_split "*fist<mode>2_floor_1"
14899   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14900         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14901                         UNSPEC_FIST_FLOOR))
14902    (clobber (reg:CC FLAGS_REG))]
14903   "TARGET_USE_FANCY_MATH_387
14904    && flag_unsafe_math_optimizations
14905    && can_create_pseudo_p ()"
14906   "#"
14907   "&& 1"
14908   [(const_int 0)]
14909 {
14910   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14911
14912   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14913   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14914   if (memory_operand (operands[0], VOIDmode))
14915     emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
14916                                       operands[2], operands[3]));
14917   else
14918     {
14919       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14920       emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
14921                                                   operands[2], operands[3],
14922                                                   operands[4]));
14923     }
14924   DONE;
14925 }
14926   [(set_attr "type" "fistp")
14927    (set_attr "i387_cw" "floor")
14928    (set_attr "mode" "<MODE>")])
14929
14930 (define_insn "fistdi2_floor"
14931   [(set (match_operand:DI 0 "memory_operand" "=m")
14932         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14933                    UNSPEC_FIST_FLOOR))
14934    (use (match_operand:HI 2 "memory_operand" "m"))
14935    (use (match_operand:HI 3 "memory_operand" "m"))
14936    (clobber (match_scratch:XF 4 "=&1f"))]
14937   "TARGET_USE_FANCY_MATH_387
14938    && flag_unsafe_math_optimizations"
14939   "* return output_fix_trunc (insn, operands, false);"
14940   [(set_attr "type" "fistp")
14941    (set_attr "i387_cw" "floor")
14942    (set_attr "mode" "DI")])
14943
14944 (define_insn "fistdi2_floor_with_temp"
14945   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14946         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14947                    UNSPEC_FIST_FLOOR))
14948    (use (match_operand:HI 2 "memory_operand" "m,m"))
14949    (use (match_operand:HI 3 "memory_operand" "m,m"))
14950    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
14951    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
14952   "TARGET_USE_FANCY_MATH_387
14953    && flag_unsafe_math_optimizations"
14954   "#"
14955   [(set_attr "type" "fistp")
14956    (set_attr "i387_cw" "floor")
14957    (set_attr "mode" "DI")])
14958
14959 (define_split
14960   [(set (match_operand:DI 0 "register_operand" "")
14961         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14962                    UNSPEC_FIST_FLOOR))
14963    (use (match_operand:HI 2 "memory_operand" ""))
14964    (use (match_operand:HI 3 "memory_operand" ""))
14965    (clobber (match_operand:DI 4 "memory_operand" ""))
14966    (clobber (match_scratch 5 ""))]
14967   "reload_completed"
14968   [(parallel [(set (match_dup 4)
14969                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
14970               (use (match_dup 2))
14971               (use (match_dup 3))
14972               (clobber (match_dup 5))])
14973    (set (match_dup 0) (match_dup 4))])
14974
14975 (define_split
14976   [(set (match_operand:DI 0 "memory_operand" "")
14977         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14978                    UNSPEC_FIST_FLOOR))
14979    (use (match_operand:HI 2 "memory_operand" ""))
14980    (use (match_operand:HI 3 "memory_operand" ""))
14981    (clobber (match_operand:DI 4 "memory_operand" ""))
14982    (clobber (match_scratch 5 ""))]
14983   "reload_completed"
14984   [(parallel [(set (match_dup 0)
14985                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
14986               (use (match_dup 2))
14987               (use (match_dup 3))
14988               (clobber (match_dup 5))])])
14989
14990 (define_insn "fist<mode>2_floor"
14991   [(set (match_operand:SWI24 0 "memory_operand" "=m")
14992         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14993                       UNSPEC_FIST_FLOOR))
14994    (use (match_operand:HI 2 "memory_operand" "m"))
14995    (use (match_operand:HI 3 "memory_operand" "m"))]
14996   "TARGET_USE_FANCY_MATH_387
14997    && flag_unsafe_math_optimizations"
14998   "* return output_fix_trunc (insn, operands, false);"
14999   [(set_attr "type" "fistp")
15000    (set_attr "i387_cw" "floor")
15001    (set_attr "mode" "<MODE>")])
15002
15003 (define_insn "fist<mode>2_floor_with_temp"
15004   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15005         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15006                       UNSPEC_FIST_FLOOR))
15007    (use (match_operand:HI 2 "memory_operand" "m,m"))
15008    (use (match_operand:HI 3 "memory_operand" "m,m"))
15009    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15010   "TARGET_USE_FANCY_MATH_387
15011    && flag_unsafe_math_optimizations"
15012   "#"
15013   [(set_attr "type" "fistp")
15014    (set_attr "i387_cw" "floor")
15015    (set_attr "mode" "<MODE>")])
15016
15017 (define_split
15018   [(set (match_operand:SWI24 0 "register_operand" "")
15019         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15020                       UNSPEC_FIST_FLOOR))
15021    (use (match_operand:HI 2 "memory_operand" ""))
15022    (use (match_operand:HI 3 "memory_operand" ""))
15023    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15024   "reload_completed"
15025   [(parallel [(set (match_dup 4)
15026                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15027               (use (match_dup 2))
15028               (use (match_dup 3))])
15029    (set (match_dup 0) (match_dup 4))])
15030
15031 (define_split
15032   [(set (match_operand:SWI24 0 "memory_operand" "")
15033         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15034                       UNSPEC_FIST_FLOOR))
15035    (use (match_operand:HI 2 "memory_operand" ""))
15036    (use (match_operand:HI 3 "memory_operand" ""))
15037    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15038   "reload_completed"
15039   [(parallel [(set (match_dup 0)
15040                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15041               (use (match_dup 2))
15042               (use (match_dup 3))])])
15043
15044 (define_expand "lfloorxf<mode>2"
15045   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15046                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15047                                    UNSPEC_FIST_FLOOR))
15048               (clobber (reg:CC FLAGS_REG))])]
15049   "TARGET_USE_FANCY_MATH_387
15050    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15051    && flag_unsafe_math_optimizations")
15052
15053 (define_expand "lfloor<MODEF:mode><SWI48:mode>2"
15054   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15055    (match_operand:MODEF 1 "register_operand" "")]
15056   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15057    && !flag_trapping_math"
15058 {
15059   if (TARGET_64BIT && optimize_insn_for_size_p ())
15060     FAIL;
15061   ix86_expand_lfloorceil (operands[0], operands[1], true);
15062   DONE;
15063 })
15064
15065 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15066 (define_insn_and_split "frndintxf2_ceil"
15067   [(set (match_operand:XF 0 "register_operand" "")
15068         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15069          UNSPEC_FRNDINT_CEIL))
15070    (clobber (reg:CC FLAGS_REG))]
15071   "TARGET_USE_FANCY_MATH_387
15072    && flag_unsafe_math_optimizations
15073    && can_create_pseudo_p ()"
15074   "#"
15075   "&& 1"
15076   [(const_int 0)]
15077 {
15078   ix86_optimize_mode_switching[I387_CEIL] = 1;
15079
15080   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15081   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15082
15083   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
15084                                        operands[2], operands[3]));
15085   DONE;
15086 }
15087   [(set_attr "type" "frndint")
15088    (set_attr "i387_cw" "ceil")
15089    (set_attr "mode" "XF")])
15090
15091 (define_insn "frndintxf2_ceil_i387"
15092   [(set (match_operand:XF 0 "register_operand" "=f")
15093         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15094          UNSPEC_FRNDINT_CEIL))
15095    (use (match_operand:HI 2 "memory_operand" "m"))
15096    (use (match_operand:HI 3 "memory_operand" "m"))]
15097   "TARGET_USE_FANCY_MATH_387
15098    && flag_unsafe_math_optimizations"
15099   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15100   [(set_attr "type" "frndint")
15101    (set_attr "i387_cw" "ceil")
15102    (set_attr "mode" "XF")])
15103
15104 (define_expand "ceilxf2"
15105   [(use (match_operand:XF 0 "register_operand" ""))
15106    (use (match_operand:XF 1 "register_operand" ""))]
15107   "TARGET_USE_FANCY_MATH_387
15108    && flag_unsafe_math_optimizations"
15109 {
15110   if (optimize_insn_for_size_p ())
15111     FAIL;
15112   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
15113   DONE;
15114 })
15115
15116 (define_expand "ceil<mode>2"
15117   [(use (match_operand:MODEF 0 "register_operand" ""))
15118    (use (match_operand:MODEF 1 "register_operand" ""))]
15119   "(TARGET_USE_FANCY_MATH_387
15120     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15121         || TARGET_MIX_SSE_I387)
15122     && flag_unsafe_math_optimizations)
15123    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15124        && !flag_trapping_math)"
15125 {
15126   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15127       && !flag_trapping_math)
15128     {
15129       if (TARGET_ROUND)
15130         emit_insn (gen_sse4_1_round<mode>2
15131                    (operands[0], operands[1], GEN_INT (ROUND_CEIL)));
15132       else if (optimize_insn_for_size_p ())
15133         FAIL;
15134       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15135         ix86_expand_floorceil (operands[0], operands[1], false);
15136       else
15137         ix86_expand_floorceildf_32 (operands[0], operands[1], false);
15138     }
15139   else
15140     {
15141       rtx op0, op1;
15142
15143       if (optimize_insn_for_size_p ())
15144         FAIL;
15145
15146       op0 = gen_reg_rtx (XFmode);
15147       op1 = gen_reg_rtx (XFmode);
15148       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15149       emit_insn (gen_frndintxf2_ceil (op0, op1));
15150
15151       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15152     }
15153   DONE;
15154 })
15155
15156 (define_insn_and_split "*fist<mode>2_ceil_1"
15157   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15158         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15159                         UNSPEC_FIST_CEIL))
15160    (clobber (reg:CC FLAGS_REG))]
15161   "TARGET_USE_FANCY_MATH_387
15162    && flag_unsafe_math_optimizations
15163    && can_create_pseudo_p ()"
15164   "#"
15165   "&& 1"
15166   [(const_int 0)]
15167 {
15168   ix86_optimize_mode_switching[I387_CEIL] = 1;
15169
15170   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15171   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15172   if (memory_operand (operands[0], VOIDmode))
15173     emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
15174                                      operands[2], operands[3]));
15175   else
15176     {
15177       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
15178       emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
15179                                                  operands[2], operands[3],
15180                                                  operands[4]));
15181     }
15182   DONE;
15183 }
15184   [(set_attr "type" "fistp")
15185    (set_attr "i387_cw" "ceil")
15186    (set_attr "mode" "<MODE>")])
15187
15188 (define_insn "fistdi2_ceil"
15189   [(set (match_operand:DI 0 "memory_operand" "=m")
15190         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
15191                    UNSPEC_FIST_CEIL))
15192    (use (match_operand:HI 2 "memory_operand" "m"))
15193    (use (match_operand:HI 3 "memory_operand" "m"))
15194    (clobber (match_scratch:XF 4 "=&1f"))]
15195   "TARGET_USE_FANCY_MATH_387
15196    && flag_unsafe_math_optimizations"
15197   "* return output_fix_trunc (insn, operands, false);"
15198   [(set_attr "type" "fistp")
15199    (set_attr "i387_cw" "ceil")
15200    (set_attr "mode" "DI")])
15201
15202 (define_insn "fistdi2_ceil_with_temp"
15203   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
15204         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
15205                    UNSPEC_FIST_CEIL))
15206    (use (match_operand:HI 2 "memory_operand" "m,m"))
15207    (use (match_operand:HI 3 "memory_operand" "m,m"))
15208    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
15209    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
15210   "TARGET_USE_FANCY_MATH_387
15211    && flag_unsafe_math_optimizations"
15212   "#"
15213   [(set_attr "type" "fistp")
15214    (set_attr "i387_cw" "ceil")
15215    (set_attr "mode" "DI")])
15216
15217 (define_split
15218   [(set (match_operand:DI 0 "register_operand" "")
15219         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15220                    UNSPEC_FIST_CEIL))
15221    (use (match_operand:HI 2 "memory_operand" ""))
15222    (use (match_operand:HI 3 "memory_operand" ""))
15223    (clobber (match_operand:DI 4 "memory_operand" ""))
15224    (clobber (match_scratch 5 ""))]
15225   "reload_completed"
15226   [(parallel [(set (match_dup 4)
15227                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15228               (use (match_dup 2))
15229               (use (match_dup 3))
15230               (clobber (match_dup 5))])
15231    (set (match_dup 0) (match_dup 4))])
15232
15233 (define_split
15234   [(set (match_operand:DI 0 "memory_operand" "")
15235         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15236                    UNSPEC_FIST_CEIL))
15237    (use (match_operand:HI 2 "memory_operand" ""))
15238    (use (match_operand:HI 3 "memory_operand" ""))
15239    (clobber (match_operand:DI 4 "memory_operand" ""))
15240    (clobber (match_scratch 5 ""))]
15241   "reload_completed"
15242   [(parallel [(set (match_dup 0)
15243                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15244               (use (match_dup 2))
15245               (use (match_dup 3))
15246               (clobber (match_dup 5))])])
15247
15248 (define_insn "fist<mode>2_ceil"
15249   [(set (match_operand:SWI24 0 "memory_operand" "=m")
15250         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
15251                       UNSPEC_FIST_CEIL))
15252    (use (match_operand:HI 2 "memory_operand" "m"))
15253    (use (match_operand:HI 3 "memory_operand" "m"))]
15254   "TARGET_USE_FANCY_MATH_387
15255    && flag_unsafe_math_optimizations"
15256   "* return output_fix_trunc (insn, operands, false);"
15257   [(set_attr "type" "fistp")
15258    (set_attr "i387_cw" "ceil")
15259    (set_attr "mode" "<MODE>")])
15260
15261 (define_insn "fist<mode>2_ceil_with_temp"
15262   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15263         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15264                       UNSPEC_FIST_CEIL))
15265    (use (match_operand:HI 2 "memory_operand" "m,m"))
15266    (use (match_operand:HI 3 "memory_operand" "m,m"))
15267    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15268   "TARGET_USE_FANCY_MATH_387
15269    && flag_unsafe_math_optimizations"
15270   "#"
15271   [(set_attr "type" "fistp")
15272    (set_attr "i387_cw" "ceil")
15273    (set_attr "mode" "<MODE>")])
15274
15275 (define_split
15276   [(set (match_operand:SWI24 0 "register_operand" "")
15277         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15278                       UNSPEC_FIST_CEIL))
15279    (use (match_operand:HI 2 "memory_operand" ""))
15280    (use (match_operand:HI 3 "memory_operand" ""))
15281    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15282   "reload_completed"
15283   [(parallel [(set (match_dup 4)
15284                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15285               (use (match_dup 2))
15286               (use (match_dup 3))])
15287    (set (match_dup 0) (match_dup 4))])
15288
15289 (define_split
15290   [(set (match_operand:SWI24 0 "memory_operand" "")
15291         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15292                       UNSPEC_FIST_CEIL))
15293    (use (match_operand:HI 2 "memory_operand" ""))
15294    (use (match_operand:HI 3 "memory_operand" ""))
15295    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15296   "reload_completed"
15297   [(parallel [(set (match_dup 0)
15298                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15299               (use (match_dup 2))
15300               (use (match_dup 3))])])
15301
15302 (define_expand "lceilxf<mode>2"
15303   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15304                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15305                                    UNSPEC_FIST_CEIL))
15306               (clobber (reg:CC FLAGS_REG))])]
15307   "TARGET_USE_FANCY_MATH_387
15308    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15309    && flag_unsafe_math_optimizations")
15310
15311 (define_expand "lceil<MODEF:mode><SWI48:mode>2"
15312   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15313    (match_operand:MODEF 1 "register_operand" "")]
15314   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15315    && !flag_trapping_math"
15316 {
15317   ix86_expand_lfloorceil (operands[0], operands[1], false);
15318   DONE;
15319 })
15320
15321 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15322 (define_insn_and_split "frndintxf2_trunc"
15323   [(set (match_operand:XF 0 "register_operand" "")
15324         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15325          UNSPEC_FRNDINT_TRUNC))
15326    (clobber (reg:CC FLAGS_REG))]
15327   "TARGET_USE_FANCY_MATH_387
15328    && flag_unsafe_math_optimizations
15329    && can_create_pseudo_p ()"
15330   "#"
15331   "&& 1"
15332   [(const_int 0)]
15333 {
15334   ix86_optimize_mode_switching[I387_TRUNC] = 1;
15335
15336   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15337   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
15338
15339   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
15340                                         operands[2], operands[3]));
15341   DONE;
15342 }
15343   [(set_attr "type" "frndint")
15344    (set_attr "i387_cw" "trunc")
15345    (set_attr "mode" "XF")])
15346
15347 (define_insn "frndintxf2_trunc_i387"
15348   [(set (match_operand:XF 0 "register_operand" "=f")
15349         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15350          UNSPEC_FRNDINT_TRUNC))
15351    (use (match_operand:HI 2 "memory_operand" "m"))
15352    (use (match_operand:HI 3 "memory_operand" "m"))]
15353   "TARGET_USE_FANCY_MATH_387
15354    && flag_unsafe_math_optimizations"
15355   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15356   [(set_attr "type" "frndint")
15357    (set_attr "i387_cw" "trunc")
15358    (set_attr "mode" "XF")])
15359
15360 (define_expand "btruncxf2"
15361   [(use (match_operand:XF 0 "register_operand" ""))
15362    (use (match_operand:XF 1 "register_operand" ""))]
15363   "TARGET_USE_FANCY_MATH_387
15364    && flag_unsafe_math_optimizations"
15365 {
15366   if (optimize_insn_for_size_p ())
15367     FAIL;
15368   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
15369   DONE;
15370 })
15371
15372 (define_expand "btrunc<mode>2"
15373   [(use (match_operand:MODEF 0 "register_operand" ""))
15374    (use (match_operand:MODEF 1 "register_operand" ""))]
15375   "(TARGET_USE_FANCY_MATH_387
15376     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15377         || TARGET_MIX_SSE_I387)
15378     && flag_unsafe_math_optimizations)
15379    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15380        && !flag_trapping_math)"
15381 {
15382   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15383       && !flag_trapping_math)
15384     {
15385       if (TARGET_ROUND)
15386         emit_insn (gen_sse4_1_round<mode>2
15387                    (operands[0], operands[1], GEN_INT (ROUND_TRUNC)));
15388       else if (optimize_insn_for_size_p ())
15389         FAIL;
15390       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15391         ix86_expand_trunc (operands[0], operands[1]);
15392       else
15393         ix86_expand_truncdf_32 (operands[0], operands[1]);
15394     }
15395   else
15396     {
15397       rtx op0, op1;
15398
15399       if (optimize_insn_for_size_p ())
15400         FAIL;
15401
15402       op0 = gen_reg_rtx (XFmode);
15403       op1 = gen_reg_rtx (XFmode);
15404       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15405       emit_insn (gen_frndintxf2_trunc (op0, op1));
15406
15407       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15408     }
15409   DONE;
15410 })
15411
15412 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15413 (define_insn_and_split "frndintxf2_mask_pm"
15414   [(set (match_operand:XF 0 "register_operand" "")
15415         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15416          UNSPEC_FRNDINT_MASK_PM))
15417    (clobber (reg:CC FLAGS_REG))]
15418   "TARGET_USE_FANCY_MATH_387
15419    && flag_unsafe_math_optimizations
15420    && can_create_pseudo_p ()"
15421   "#"
15422   "&& 1"
15423   [(const_int 0)]
15424 {
15425   ix86_optimize_mode_switching[I387_MASK_PM] = 1;
15426
15427   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15428   operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
15429
15430   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
15431                                           operands[2], operands[3]));
15432   DONE;
15433 }
15434   [(set_attr "type" "frndint")
15435    (set_attr "i387_cw" "mask_pm")
15436    (set_attr "mode" "XF")])
15437
15438 (define_insn "frndintxf2_mask_pm_i387"
15439   [(set (match_operand:XF 0 "register_operand" "=f")
15440         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15441          UNSPEC_FRNDINT_MASK_PM))
15442    (use (match_operand:HI 2 "memory_operand" "m"))
15443    (use (match_operand:HI 3 "memory_operand" "m"))]
15444   "TARGET_USE_FANCY_MATH_387
15445    && flag_unsafe_math_optimizations"
15446   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
15447   [(set_attr "type" "frndint")
15448    (set_attr "i387_cw" "mask_pm")
15449    (set_attr "mode" "XF")])
15450
15451 (define_expand "nearbyintxf2"
15452   [(use (match_operand:XF 0 "register_operand" ""))
15453    (use (match_operand:XF 1 "register_operand" ""))]
15454   "TARGET_USE_FANCY_MATH_387
15455    && flag_unsafe_math_optimizations"
15456 {
15457   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
15458   DONE;
15459 })
15460
15461 (define_expand "nearbyint<mode>2"
15462   [(use (match_operand:MODEF 0 "register_operand" ""))
15463    (use (match_operand:MODEF 1 "register_operand" ""))]
15464   "TARGET_USE_FANCY_MATH_387
15465    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15466        || TARGET_MIX_SSE_I387)
15467    && flag_unsafe_math_optimizations"
15468 {
15469   rtx op0 = gen_reg_rtx (XFmode);
15470   rtx op1 = gen_reg_rtx (XFmode);
15471
15472   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15473   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
15474
15475   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15476   DONE;
15477 })
15478
15479 (define_insn "fxam<mode>2_i387"
15480   [(set (match_operand:HI 0 "register_operand" "=a")
15481         (unspec:HI
15482           [(match_operand:X87MODEF 1 "register_operand" "f")]
15483           UNSPEC_FXAM))]
15484   "TARGET_USE_FANCY_MATH_387"
15485   "fxam\n\tfnstsw\t%0"
15486   [(set_attr "type" "multi")
15487    (set_attr "length" "4")
15488    (set_attr "unit" "i387")
15489    (set_attr "mode" "<MODE>")])
15490
15491 (define_insn_and_split "fxam<mode>2_i387_with_temp"
15492   [(set (match_operand:HI 0 "register_operand" "")
15493         (unspec:HI
15494           [(match_operand:MODEF 1 "memory_operand" "")]
15495           UNSPEC_FXAM_MEM))]
15496   "TARGET_USE_FANCY_MATH_387
15497    && can_create_pseudo_p ()"
15498   "#"
15499   "&& 1"
15500   [(set (match_dup 2)(match_dup 1))
15501    (set (match_dup 0)
15502         (unspec:HI [(match_dup 2)] UNSPEC_FXAM))]
15503 {
15504   operands[2] = gen_reg_rtx (<MODE>mode);
15505
15506   MEM_VOLATILE_P (operands[1]) = 1;
15507 }
15508   [(set_attr "type" "multi")
15509    (set_attr "unit" "i387")
15510    (set_attr "mode" "<MODE>")])
15511
15512 (define_expand "isinfxf2"
15513   [(use (match_operand:SI 0 "register_operand" ""))
15514    (use (match_operand:XF 1 "register_operand" ""))]
15515   "TARGET_USE_FANCY_MATH_387
15516    && TARGET_C99_FUNCTIONS"
15517 {
15518   rtx mask = GEN_INT (0x45);
15519   rtx val = GEN_INT (0x05);
15520
15521   rtx cond;
15522
15523   rtx scratch = gen_reg_rtx (HImode);
15524   rtx res = gen_reg_rtx (QImode);
15525
15526   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
15527
15528   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
15529   emit_insn (gen_cmpqi_ext_3 (scratch, val));
15530   cond = gen_rtx_fmt_ee (EQ, QImode,
15531                          gen_rtx_REG (CCmode, FLAGS_REG),
15532                          const0_rtx);
15533   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
15534   emit_insn (gen_zero_extendqisi2 (operands[0], res));
15535   DONE;
15536 })
15537
15538 (define_expand "isinf<mode>2"
15539   [(use (match_operand:SI 0 "register_operand" ""))
15540    (use (match_operand:MODEF 1 "nonimmediate_operand" ""))]
15541   "TARGET_USE_FANCY_MATH_387
15542    && TARGET_C99_FUNCTIONS
15543    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
15544 {
15545   rtx mask = GEN_INT (0x45);
15546   rtx val = GEN_INT (0x05);
15547
15548   rtx cond;
15549
15550   rtx scratch = gen_reg_rtx (HImode);
15551   rtx res = gen_reg_rtx (QImode);
15552
15553   /* Remove excess precision by forcing value through memory. */
15554   if (memory_operand (operands[1], VOIDmode))
15555     emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, operands[1]));
15556   else
15557     {
15558       rtx temp = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
15559
15560       emit_move_insn (temp, operands[1]);
15561       emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, temp));
15562     }
15563
15564   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
15565   emit_insn (gen_cmpqi_ext_3 (scratch, val));
15566   cond = gen_rtx_fmt_ee (EQ, QImode,
15567                          gen_rtx_REG (CCmode, FLAGS_REG),
15568                          const0_rtx);
15569   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
15570   emit_insn (gen_zero_extendqisi2 (operands[0], res));
15571   DONE;
15572 })
15573
15574 (define_expand "signbitxf2"
15575   [(use (match_operand:SI 0 "register_operand" ""))
15576    (use (match_operand:XF 1 "register_operand" ""))]
15577   "TARGET_USE_FANCY_MATH_387"
15578 {
15579   rtx scratch = gen_reg_rtx (HImode);
15580
15581   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
15582   emit_insn (gen_andsi3 (operands[0],
15583              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15584   DONE;
15585 })
15586
15587 (define_insn "movmsk_df"
15588   [(set (match_operand:SI 0 "register_operand" "=r")
15589         (unspec:SI
15590           [(match_operand:DF 1 "register_operand" "x")]
15591           UNSPEC_MOVMSK))]
15592   "SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH"
15593   "%vmovmskpd\t{%1, %0|%0, %1}"
15594   [(set_attr "type" "ssemov")
15595    (set_attr "prefix" "maybe_vex")
15596    (set_attr "mode" "DF")])
15597
15598 ;; Use movmskpd in SSE mode to avoid store forwarding stall
15599 ;; for 32bit targets and movq+shrq sequence for 64bit targets.
15600 (define_expand "signbitdf2"
15601   [(use (match_operand:SI 0 "register_operand" ""))
15602    (use (match_operand:DF 1 "register_operand" ""))]
15603   "TARGET_USE_FANCY_MATH_387
15604    || (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)"
15605 {
15606   if (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)
15607     {
15608       emit_insn (gen_movmsk_df (operands[0], operands[1]));
15609       emit_insn (gen_andsi3 (operands[0], operands[0], const1_rtx));
15610     }
15611   else
15612     {
15613       rtx scratch = gen_reg_rtx (HImode);
15614
15615       emit_insn (gen_fxamdf2_i387 (scratch, operands[1]));
15616       emit_insn (gen_andsi3 (operands[0],
15617                  gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15618     }
15619   DONE;
15620 })
15621
15622 (define_expand "signbitsf2"
15623   [(use (match_operand:SI 0 "register_operand" ""))
15624    (use (match_operand:SF 1 "register_operand" ""))]
15625   "TARGET_USE_FANCY_MATH_387
15626    && !(SSE_FLOAT_MODE_P (SFmode) && TARGET_SSE_MATH)"
15627 {
15628   rtx scratch = gen_reg_rtx (HImode);
15629
15630   emit_insn (gen_fxamsf2_i387 (scratch, operands[1]));
15631   emit_insn (gen_andsi3 (operands[0],
15632              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15633   DONE;
15634 })
15635 \f
15636 ;; Block operation instructions
15637
15638 (define_insn "cld"
15639   [(unspec_volatile [(const_int 0)] UNSPECV_CLD)]
15640   ""
15641   "cld"
15642   [(set_attr "length" "1")
15643    (set_attr "length_immediate" "0")
15644    (set_attr "modrm" "0")])
15645
15646 (define_expand "movmem<mode>"
15647   [(use (match_operand:BLK 0 "memory_operand" ""))
15648    (use (match_operand:BLK 1 "memory_operand" ""))
15649    (use (match_operand:SWI48 2 "nonmemory_operand" ""))
15650    (use (match_operand:SWI48 3 "const_int_operand" ""))
15651    (use (match_operand:SI 4 "const_int_operand" ""))
15652    (use (match_operand:SI 5 "const_int_operand" ""))]
15653   ""
15654 {
15655  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
15656                          operands[4], operands[5]))
15657    DONE;
15658  else
15659    FAIL;
15660 })
15661
15662 ;; Most CPUs don't like single string operations
15663 ;; Handle this case here to simplify previous expander.
15664
15665 (define_expand "strmov"
15666   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
15667    (set (match_operand 1 "memory_operand" "") (match_dup 4))
15668    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
15669               (clobber (reg:CC FLAGS_REG))])
15670    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
15671               (clobber (reg:CC FLAGS_REG))])]
15672   ""
15673 {
15674   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
15675
15676   /* If .md ever supports :P for Pmode, these can be directly
15677      in the pattern above.  */
15678   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
15679   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
15680
15681   /* Can't use this if the user has appropriated esi or edi.  */
15682   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15683       && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
15684     {
15685       emit_insn (gen_strmov_singleop (operands[0], operands[1],
15686                                       operands[2], operands[3],
15687                                       operands[5], operands[6]));
15688       DONE;
15689     }
15690
15691   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
15692 })
15693
15694 (define_expand "strmov_singleop"
15695   [(parallel [(set (match_operand 1 "memory_operand" "")
15696                    (match_operand 3 "memory_operand" ""))
15697               (set (match_operand 0 "register_operand" "")
15698                    (match_operand 4 "" ""))
15699               (set (match_operand 2 "register_operand" "")
15700                    (match_operand 5 "" ""))])]
15701   ""
15702   "ix86_current_function_needs_cld = 1;")
15703
15704 (define_insn "*strmovdi_rex_1"
15705   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
15706         (mem:DI (match_operand:DI 3 "register_operand" "1")))
15707    (set (match_operand:DI 0 "register_operand" "=D")
15708         (plus:DI (match_dup 2)
15709                  (const_int 8)))
15710    (set (match_operand:DI 1 "register_operand" "=S")
15711         (plus:DI (match_dup 3)
15712                  (const_int 8)))]
15713   "TARGET_64BIT
15714    && !(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15715   "movsq"
15716   [(set_attr "type" "str")
15717    (set_attr "memory" "both")
15718    (set_attr "mode" "DI")])
15719
15720 (define_insn "*strmovsi_1"
15721   [(set (mem:SI (match_operand:P 2 "register_operand" "0"))
15722         (mem:SI (match_operand:P 3 "register_operand" "1")))
15723    (set (match_operand:P 0 "register_operand" "=D")
15724         (plus:P (match_dup 2)
15725                 (const_int 4)))
15726    (set (match_operand:P 1 "register_operand" "=S")
15727         (plus:P (match_dup 3)
15728                 (const_int 4)))]
15729   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15730   "movs{l|d}"
15731   [(set_attr "type" "str")
15732    (set_attr "memory" "both")
15733    (set_attr "mode" "SI")])
15734
15735 (define_insn "*strmovhi_1"
15736   [(set (mem:HI (match_operand:P 2 "register_operand" "0"))
15737         (mem:HI (match_operand:P 3 "register_operand" "1")))
15738    (set (match_operand:P 0 "register_operand" "=D")
15739         (plus:P (match_dup 2)
15740                 (const_int 2)))
15741    (set (match_operand:P 1 "register_operand" "=S")
15742         (plus:P (match_dup 3)
15743                 (const_int 2)))]
15744   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15745   "movsw"
15746   [(set_attr "type" "str")
15747    (set_attr "memory" "both")
15748    (set_attr "mode" "HI")])
15749
15750 (define_insn "*strmovqi_1"
15751   [(set (mem:QI (match_operand:P 2 "register_operand" "0"))
15752         (mem:QI (match_operand:P 3 "register_operand" "1")))
15753    (set (match_operand:P 0 "register_operand" "=D")
15754         (plus:P (match_dup 2)
15755                 (const_int 1)))
15756    (set (match_operand:P 1 "register_operand" "=S")
15757         (plus:P (match_dup 3)
15758                 (const_int 1)))]
15759   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15760   "movsb"
15761   [(set_attr "type" "str")
15762    (set_attr "memory" "both")
15763    (set (attr "prefix_rex")
15764         (if_then_else
15765           (match_test "<P:MODE>mode == DImode")
15766           (const_string "0")
15767           (const_string "*")))
15768    (set_attr "mode" "QI")])
15769
15770 (define_expand "rep_mov"
15771   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
15772               (set (match_operand 0 "register_operand" "")
15773                    (match_operand 5 "" ""))
15774               (set (match_operand 2 "register_operand" "")
15775                    (match_operand 6 "" ""))
15776               (set (match_operand 1 "memory_operand" "")
15777                    (match_operand 3 "memory_operand" ""))
15778               (use (match_dup 4))])]
15779   ""
15780   "ix86_current_function_needs_cld = 1;")
15781
15782 (define_insn "*rep_movdi_rex64"
15783   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15784    (set (match_operand:DI 0 "register_operand" "=D")
15785         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
15786                             (const_int 3))
15787                  (match_operand:DI 3 "register_operand" "0")))
15788    (set (match_operand:DI 1 "register_operand" "=S")
15789         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
15790                  (match_operand:DI 4 "register_operand" "1")))
15791    (set (mem:BLK (match_dup 3))
15792         (mem:BLK (match_dup 4)))
15793    (use (match_dup 5))]
15794   "TARGET_64BIT
15795    && !(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15796   "rep{%;} movsq"
15797   [(set_attr "type" "str")
15798    (set_attr "prefix_rep" "1")
15799    (set_attr "memory" "both")
15800    (set_attr "mode" "DI")])
15801
15802 (define_insn "*rep_movsi"
15803   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15804    (set (match_operand:P 0 "register_operand" "=D")
15805         (plus:P (ashift:P (match_operand:P 5 "register_operand" "2")
15806                           (const_int 2))
15807                  (match_operand:P 3 "register_operand" "0")))
15808    (set (match_operand:P 1 "register_operand" "=S")
15809         (plus:P (ashift:P (match_dup 5) (const_int 2))
15810                 (match_operand:P 4 "register_operand" "1")))
15811    (set (mem:BLK (match_dup 3))
15812         (mem:BLK (match_dup 4)))
15813    (use (match_dup 5))]
15814   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15815   "rep{%;} movs{l|d}"
15816   [(set_attr "type" "str")
15817    (set_attr "prefix_rep" "1")
15818    (set_attr "memory" "both")
15819    (set_attr "mode" "SI")])
15820
15821 (define_insn "*rep_movqi"
15822   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15823    (set (match_operand:P 0 "register_operand" "=D")
15824         (plus:P (match_operand:P 3 "register_operand" "0")
15825                 (match_operand:P 5 "register_operand" "2")))
15826    (set (match_operand:P 1 "register_operand" "=S")
15827         (plus:P (match_operand:P 4 "register_operand" "1") (match_dup 5)))
15828    (set (mem:BLK (match_dup 3))
15829         (mem:BLK (match_dup 4)))
15830    (use (match_dup 5))]
15831   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15832   "rep{%;} movsb"
15833   [(set_attr "type" "str")
15834    (set_attr "prefix_rep" "1")
15835    (set_attr "memory" "both")
15836    (set_attr "mode" "QI")])
15837
15838 (define_expand "setmem<mode>"
15839    [(use (match_operand:BLK 0 "memory_operand" ""))
15840     (use (match_operand:SWI48 1 "nonmemory_operand" ""))
15841     (use (match_operand:QI 2 "nonmemory_operand" ""))
15842     (use (match_operand 3 "const_int_operand" ""))
15843     (use (match_operand:SI 4 "const_int_operand" ""))
15844     (use (match_operand:SI 5 "const_int_operand" ""))]
15845   ""
15846 {
15847  if (ix86_expand_setmem (operands[0], operands[1],
15848                          operands[2], operands[3],
15849                          operands[4], operands[5]))
15850    DONE;
15851  else
15852    FAIL;
15853 })
15854
15855 ;; Most CPUs don't like single string operations
15856 ;; Handle this case here to simplify previous expander.
15857
15858 (define_expand "strset"
15859   [(set (match_operand 1 "memory_operand" "")
15860         (match_operand 2 "register_operand" ""))
15861    (parallel [(set (match_operand 0 "register_operand" "")
15862                    (match_dup 3))
15863               (clobber (reg:CC FLAGS_REG))])]
15864   ""
15865 {
15866   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
15867     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
15868
15869   /* If .md ever supports :P for Pmode, this can be directly
15870      in the pattern above.  */
15871   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
15872                               GEN_INT (GET_MODE_SIZE (GET_MODE
15873                                                       (operands[2]))));
15874   /* Can't use this if the user has appropriated eax or edi.  */
15875   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15876       && !(fixed_regs[AX_REG] || fixed_regs[DI_REG]))
15877     {
15878       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
15879                                       operands[3]));
15880       DONE;
15881     }
15882 })
15883
15884 (define_expand "strset_singleop"
15885   [(parallel [(set (match_operand 1 "memory_operand" "")
15886                    (match_operand 2 "register_operand" ""))
15887               (set (match_operand 0 "register_operand" "")
15888                    (match_operand 3 "" ""))])]
15889   ""
15890   "ix86_current_function_needs_cld = 1;")
15891
15892 (define_insn "*strsetdi_rex_1"
15893   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
15894         (match_operand:DI 2 "register_operand" "a"))
15895    (set (match_operand:DI 0 "register_operand" "=D")
15896         (plus:DI (match_dup 1)
15897                  (const_int 8)))]
15898   "TARGET_64BIT
15899    && !(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15900   "stosq"
15901   [(set_attr "type" "str")
15902    (set_attr "memory" "store")
15903    (set_attr "mode" "DI")])
15904
15905 (define_insn "*strsetsi_1"
15906   [(set (mem:SI (match_operand:P 1 "register_operand" "0"))
15907         (match_operand:SI 2 "register_operand" "a"))
15908    (set (match_operand:P 0 "register_operand" "=D")
15909         (plus:P (match_dup 1)
15910                 (const_int 4)))]
15911   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15912   "stos{l|d}"
15913   [(set_attr "type" "str")
15914    (set_attr "memory" "store")
15915    (set_attr "mode" "SI")])
15916
15917 (define_insn "*strsethi_1"
15918   [(set (mem:HI (match_operand:P 1 "register_operand" "0"))
15919         (match_operand:HI 2 "register_operand" "a"))
15920    (set (match_operand:P 0 "register_operand" "=D")
15921         (plus:P (match_dup 1)
15922                 (const_int 2)))]
15923   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15924   "stosw"
15925   [(set_attr "type" "str")
15926    (set_attr "memory" "store")
15927    (set_attr "mode" "HI")])
15928
15929 (define_insn "*strsetqi_1"
15930   [(set (mem:QI (match_operand:P 1 "register_operand" "0"))
15931         (match_operand:QI 2 "register_operand" "a"))
15932    (set (match_operand:P 0 "register_operand" "=D")
15933         (plus:P (match_dup 1)
15934                 (const_int 1)))]
15935   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15936   "stosb"
15937   [(set_attr "type" "str")
15938    (set_attr "memory" "store")
15939    (set (attr "prefix_rex")
15940         (if_then_else
15941           (match_test "<P:MODE>mode == DImode")
15942           (const_string "0")
15943           (const_string "*")))
15944    (set_attr "mode" "QI")])
15945
15946 (define_expand "rep_stos"
15947   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
15948               (set (match_operand 0 "register_operand" "")
15949                    (match_operand 4 "" ""))
15950               (set (match_operand 2 "memory_operand" "") (const_int 0))
15951               (use (match_operand 3 "register_operand" ""))
15952               (use (match_dup 1))])]
15953   ""
15954   "ix86_current_function_needs_cld = 1;")
15955
15956 (define_insn "*rep_stosdi_rex64"
15957   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15958    (set (match_operand:DI 0 "register_operand" "=D")
15959         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
15960                             (const_int 3))
15961                  (match_operand:DI 3 "register_operand" "0")))
15962    (set (mem:BLK (match_dup 3))
15963         (const_int 0))
15964    (use (match_operand:DI 2 "register_operand" "a"))
15965    (use (match_dup 4))]
15966   "TARGET_64BIT
15967    && !(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
15968   "rep{%;} stosq"
15969   [(set_attr "type" "str")
15970    (set_attr "prefix_rep" "1")
15971    (set_attr "memory" "store")
15972    (set_attr "mode" "DI")])
15973
15974 (define_insn "*rep_stossi"
15975   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
15976    (set (match_operand:P 0 "register_operand" "=D")
15977         (plus:P (ashift:P (match_operand:P 4 "register_operand" "1")
15978                           (const_int 2))
15979                  (match_operand:P 3 "register_operand" "0")))
15980    (set (mem:BLK (match_dup 3))
15981         (const_int 0))
15982    (use (match_operand:SI 2 "register_operand" "a"))
15983    (use (match_dup 4))]
15984   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
15985   "rep{%;} stos{l|d}"
15986   [(set_attr "type" "str")
15987    (set_attr "prefix_rep" "1")
15988    (set_attr "memory" "store")
15989    (set_attr "mode" "SI")])
15990
15991 (define_insn "*rep_stosqi"
15992   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
15993    (set (match_operand:P 0 "register_operand" "=D")
15994         (plus:P (match_operand:P 3 "register_operand" "0")
15995                 (match_operand:P 4 "register_operand" "1")))
15996    (set (mem:BLK (match_dup 3))
15997         (const_int 0))
15998    (use (match_operand:QI 2 "register_operand" "a"))
15999    (use (match_dup 4))]
16000   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16001   "rep{%;} stosb"
16002   [(set_attr "type" "str")
16003    (set_attr "prefix_rep" "1")
16004    (set_attr "memory" "store")
16005    (set (attr "prefix_rex")
16006         (if_then_else
16007           (match_test "<P:MODE>mode == DImode")
16008           (const_string "0")
16009           (const_string "*")))
16010    (set_attr "mode" "QI")])
16011
16012 (define_expand "cmpstrnsi"
16013   [(set (match_operand:SI 0 "register_operand" "")
16014         (compare:SI (match_operand:BLK 1 "general_operand" "")
16015                     (match_operand:BLK 2 "general_operand" "")))
16016    (use (match_operand 3 "general_operand" ""))
16017    (use (match_operand 4 "immediate_operand" ""))]
16018   ""
16019 {
16020   rtx addr1, addr2, out, outlow, count, countreg, align;
16021
16022   if (optimize_insn_for_size_p () && !TARGET_INLINE_ALL_STRINGOPS)
16023     FAIL;
16024
16025   /* Can't use this if the user has appropriated ecx, esi or edi.  */
16026   if (fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])
16027     FAIL;
16028
16029   out = operands[0];
16030   if (!REG_P (out))
16031     out = gen_reg_rtx (SImode);
16032
16033   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
16034   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
16035   if (addr1 != XEXP (operands[1], 0))
16036     operands[1] = replace_equiv_address_nv (operands[1], addr1);
16037   if (addr2 != XEXP (operands[2], 0))
16038     operands[2] = replace_equiv_address_nv (operands[2], addr2);
16039
16040   count = operands[3];
16041   countreg = ix86_zero_extend_to_Pmode (count);
16042
16043   /* %%% Iff we are testing strict equality, we can use known alignment
16044      to good advantage.  This may be possible with combine, particularly
16045      once cc0 is dead.  */
16046   align = operands[4];
16047
16048   if (CONST_INT_P (count))
16049     {
16050       if (INTVAL (count) == 0)
16051         {
16052           emit_move_insn (operands[0], const0_rtx);
16053           DONE;
16054         }
16055       emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
16056                                      operands[1], operands[2]));
16057     }
16058   else
16059     {
16060       rtx (*gen_cmp) (rtx, rtx);
16061
16062       gen_cmp = (TARGET_64BIT
16063                  ? gen_cmpdi_1 : gen_cmpsi_1);
16064
16065       emit_insn (gen_cmp (countreg, countreg));
16066       emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
16067                                   operands[1], operands[2]));
16068     }
16069
16070   outlow = gen_lowpart (QImode, out);
16071   emit_insn (gen_cmpintqi (outlow));
16072   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
16073
16074   if (operands[0] != out)
16075     emit_move_insn (operands[0], out);
16076
16077   DONE;
16078 })
16079
16080 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
16081
16082 (define_expand "cmpintqi"
16083   [(set (match_dup 1)
16084         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16085    (set (match_dup 2)
16086         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16087    (parallel [(set (match_operand:QI 0 "register_operand" "")
16088                    (minus:QI (match_dup 1)
16089                              (match_dup 2)))
16090               (clobber (reg:CC FLAGS_REG))])]
16091   ""
16092 {
16093   operands[1] = gen_reg_rtx (QImode);
16094   operands[2] = gen_reg_rtx (QImode);
16095 })
16096
16097 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
16098 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
16099
16100 (define_expand "cmpstrnqi_nz_1"
16101   [(parallel [(set (reg:CC FLAGS_REG)
16102                    (compare:CC (match_operand 4 "memory_operand" "")
16103                                (match_operand 5 "memory_operand" "")))
16104               (use (match_operand 2 "register_operand" ""))
16105               (use (match_operand:SI 3 "immediate_operand" ""))
16106               (clobber (match_operand 0 "register_operand" ""))
16107               (clobber (match_operand 1 "register_operand" ""))
16108               (clobber (match_dup 2))])]
16109   ""
16110   "ix86_current_function_needs_cld = 1;")
16111
16112 (define_insn "*cmpstrnqi_nz_1"
16113   [(set (reg:CC FLAGS_REG)
16114         (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16115                     (mem:BLK (match_operand:P 5 "register_operand" "1"))))
16116    (use (match_operand:P 6 "register_operand" "2"))
16117    (use (match_operand:SI 3 "immediate_operand" "i"))
16118    (clobber (match_operand:P 0 "register_operand" "=S"))
16119    (clobber (match_operand:P 1 "register_operand" "=D"))
16120    (clobber (match_operand:P 2 "register_operand" "=c"))]
16121   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16122   "repz{%;} cmpsb"
16123   [(set_attr "type" "str")
16124    (set_attr "mode" "QI")
16125    (set (attr "prefix_rex")
16126         (if_then_else
16127           (match_test "<P:MODE>mode == DImode")
16128           (const_string "0")
16129           (const_string "*")))
16130    (set_attr "prefix_rep" "1")])
16131
16132 ;; The same, but the count is not known to not be zero.
16133
16134 (define_expand "cmpstrnqi_1"
16135   [(parallel [(set (reg:CC FLAGS_REG)
16136                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
16137                                      (const_int 0))
16138                   (compare:CC (match_operand 4 "memory_operand" "")
16139                               (match_operand 5 "memory_operand" ""))
16140                   (const_int 0)))
16141               (use (match_operand:SI 3 "immediate_operand" ""))
16142               (use (reg:CC FLAGS_REG))
16143               (clobber (match_operand 0 "register_operand" ""))
16144               (clobber (match_operand 1 "register_operand" ""))
16145               (clobber (match_dup 2))])]
16146   ""
16147   "ix86_current_function_needs_cld = 1;")
16148
16149 (define_insn "*cmpstrnqi_1"
16150   [(set (reg:CC FLAGS_REG)
16151         (if_then_else:CC (ne (match_operand:P 6 "register_operand" "2")
16152                              (const_int 0))
16153           (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16154                       (mem:BLK (match_operand:P 5 "register_operand" "1")))
16155           (const_int 0)))
16156    (use (match_operand:SI 3 "immediate_operand" "i"))
16157    (use (reg:CC FLAGS_REG))
16158    (clobber (match_operand:P 0 "register_operand" "=S"))
16159    (clobber (match_operand:P 1 "register_operand" "=D"))
16160    (clobber (match_operand:P 2 "register_operand" "=c"))]
16161   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16162   "repz{%;} cmpsb"
16163   [(set_attr "type" "str")
16164    (set_attr "mode" "QI")
16165    (set (attr "prefix_rex")
16166         (if_then_else
16167           (match_test "<P:MODE>mode == DImode")
16168           (const_string "0")
16169           (const_string "*")))
16170    (set_attr "prefix_rep" "1")])
16171
16172 (define_expand "strlen<mode>"
16173   [(set (match_operand:P 0 "register_operand" "")
16174         (unspec:P [(match_operand:BLK 1 "general_operand" "")
16175                    (match_operand:QI 2 "immediate_operand" "")
16176                    (match_operand 3 "immediate_operand" "")]
16177                   UNSPEC_SCAS))]
16178   ""
16179 {
16180  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
16181    DONE;
16182  else
16183    FAIL;
16184 })
16185
16186 (define_expand "strlenqi_1"
16187   [(parallel [(set (match_operand 0 "register_operand" "")
16188                    (match_operand 2 "" ""))
16189               (clobber (match_operand 1 "register_operand" ""))
16190               (clobber (reg:CC FLAGS_REG))])]
16191   ""
16192   "ix86_current_function_needs_cld = 1;")
16193
16194 (define_insn "*strlenqi_1"
16195   [(set (match_operand:P 0 "register_operand" "=&c")
16196         (unspec:P [(mem:BLK (match_operand:P 5 "register_operand" "1"))
16197                    (match_operand:QI 2 "register_operand" "a")
16198                    (match_operand:P 3 "immediate_operand" "i")
16199                    (match_operand:P 4 "register_operand" "0")] UNSPEC_SCAS))
16200    (clobber (match_operand:P 1 "register_operand" "=D"))
16201    (clobber (reg:CC FLAGS_REG))]
16202   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16203   "repnz{%;} scasb"
16204   [(set_attr "type" "str")
16205    (set_attr "mode" "QI")
16206    (set (attr "prefix_rex")
16207         (if_then_else
16208           (match_test "<P:MODE>mode == DImode")
16209           (const_string "0")
16210           (const_string "*")))
16211    (set_attr "prefix_rep" "1")])
16212
16213 ;; Peephole optimizations to clean up after cmpstrn*.  This should be
16214 ;; handled in combine, but it is not currently up to the task.
16215 ;; When used for their truth value, the cmpstrn* expanders generate
16216 ;; code like this:
16217 ;;
16218 ;;   repz cmpsb
16219 ;;   seta       %al
16220 ;;   setb       %dl
16221 ;;   cmpb       %al, %dl
16222 ;;   jcc        label
16223 ;;
16224 ;; The intermediate three instructions are unnecessary.
16225
16226 ;; This one handles cmpstrn*_nz_1...
16227 (define_peephole2
16228   [(parallel[
16229      (set (reg:CC FLAGS_REG)
16230           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16231                       (mem:BLK (match_operand 5 "register_operand" ""))))
16232      (use (match_operand 6 "register_operand" ""))
16233      (use (match_operand:SI 3 "immediate_operand" ""))
16234      (clobber (match_operand 0 "register_operand" ""))
16235      (clobber (match_operand 1 "register_operand" ""))
16236      (clobber (match_operand 2 "register_operand" ""))])
16237    (set (match_operand:QI 7 "register_operand" "")
16238         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16239    (set (match_operand:QI 8 "register_operand" "")
16240         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16241    (set (reg FLAGS_REG)
16242         (compare (match_dup 7) (match_dup 8)))
16243   ]
16244   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16245   [(parallel[
16246      (set (reg:CC FLAGS_REG)
16247           (compare:CC (mem:BLK (match_dup 4))
16248                       (mem:BLK (match_dup 5))))
16249      (use (match_dup 6))
16250      (use (match_dup 3))
16251      (clobber (match_dup 0))
16252      (clobber (match_dup 1))
16253      (clobber (match_dup 2))])])
16254
16255 ;; ...and this one handles cmpstrn*_1.
16256 (define_peephole2
16257   [(parallel[
16258      (set (reg:CC FLAGS_REG)
16259           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
16260                                (const_int 0))
16261             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16262                         (mem:BLK (match_operand 5 "register_operand" "")))
16263             (const_int 0)))
16264      (use (match_operand:SI 3 "immediate_operand" ""))
16265      (use (reg:CC FLAGS_REG))
16266      (clobber (match_operand 0 "register_operand" ""))
16267      (clobber (match_operand 1 "register_operand" ""))
16268      (clobber (match_operand 2 "register_operand" ""))])
16269    (set (match_operand:QI 7 "register_operand" "")
16270         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16271    (set (match_operand:QI 8 "register_operand" "")
16272         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16273    (set (reg FLAGS_REG)
16274         (compare (match_dup 7) (match_dup 8)))
16275   ]
16276   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16277   [(parallel[
16278      (set (reg:CC FLAGS_REG)
16279           (if_then_else:CC (ne (match_dup 6)
16280                                (const_int 0))
16281             (compare:CC (mem:BLK (match_dup 4))
16282                         (mem:BLK (match_dup 5)))
16283             (const_int 0)))
16284      (use (match_dup 3))
16285      (use (reg:CC FLAGS_REG))
16286      (clobber (match_dup 0))
16287      (clobber (match_dup 1))
16288      (clobber (match_dup 2))])])
16289 \f
16290 ;; Conditional move instructions.
16291
16292 (define_expand "mov<mode>cc"
16293   [(set (match_operand:SWIM 0 "register_operand" "")
16294         (if_then_else:SWIM (match_operand 1 "ordered_comparison_operator" "")
16295                            (match_operand:SWIM 2 "<general_operand>" "")
16296                            (match_operand:SWIM 3 "<general_operand>" "")))]
16297   ""
16298   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
16299
16300 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
16301 ;; the register first winds up with `sbbl $0,reg', which is also weird.
16302 ;; So just document what we're doing explicitly.
16303
16304 (define_expand "x86_mov<mode>cc_0_m1"
16305   [(parallel
16306     [(set (match_operand:SWI48 0 "register_operand" "")
16307           (if_then_else:SWI48
16308             (match_operator:SWI48 2 "ix86_carry_flag_operator"
16309              [(match_operand 1 "flags_reg_operand" "")
16310               (const_int 0)])
16311             (const_int -1)
16312             (const_int 0)))
16313      (clobber (reg:CC FLAGS_REG))])])
16314
16315 (define_insn "*x86_mov<mode>cc_0_m1"
16316   [(set (match_operand:SWI48 0 "register_operand" "=r")
16317         (if_then_else:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16318                              [(reg FLAGS_REG) (const_int 0)])
16319           (const_int -1)
16320           (const_int 0)))
16321    (clobber (reg:CC FLAGS_REG))]
16322   ""
16323   "sbb{<imodesuffix>}\t%0, %0"
16324   ; Since we don't have the proper number of operands for an alu insn,
16325   ; fill in all the blanks.
16326   [(set_attr "type" "alu")
16327    (set_attr "use_carry" "1")
16328    (set_attr "pent_pair" "pu")
16329    (set_attr "memory" "none")
16330    (set_attr "imm_disp" "false")
16331    (set_attr "mode" "<MODE>")
16332    (set_attr "length_immediate" "0")])
16333
16334 (define_insn "*x86_mov<mode>cc_0_m1_se"
16335   [(set (match_operand:SWI48 0 "register_operand" "=r")
16336         (sign_extract:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16337                              [(reg FLAGS_REG) (const_int 0)])
16338                             (const_int 1)
16339                             (const_int 0)))
16340    (clobber (reg:CC FLAGS_REG))]
16341   ""
16342   "sbb{<imodesuffix>}\t%0, %0"
16343   [(set_attr "type" "alu")
16344    (set_attr "use_carry" "1")
16345    (set_attr "pent_pair" "pu")
16346    (set_attr "memory" "none")
16347    (set_attr "imm_disp" "false")
16348    (set_attr "mode" "<MODE>")
16349    (set_attr "length_immediate" "0")])
16350
16351 (define_insn "*x86_mov<mode>cc_0_m1_neg"
16352   [(set (match_operand:SWI48 0 "register_operand" "=r")
16353         (neg:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16354                     [(reg FLAGS_REG) (const_int 0)])))
16355    (clobber (reg:CC FLAGS_REG))]
16356   ""
16357   "sbb{<imodesuffix>}\t%0, %0"
16358   [(set_attr "type" "alu")
16359    (set_attr "use_carry" "1")
16360    (set_attr "pent_pair" "pu")
16361    (set_attr "memory" "none")
16362    (set_attr "imm_disp" "false")
16363    (set_attr "mode" "<MODE>")
16364    (set_attr "length_immediate" "0")])
16365
16366 (define_insn "*mov<mode>cc_noc"
16367   [(set (match_operand:SWI248 0 "register_operand" "=r,r")
16368         (if_then_else:SWI248 (match_operator 1 "ix86_comparison_operator"
16369                                [(reg FLAGS_REG) (const_int 0)])
16370           (match_operand:SWI248 2 "nonimmediate_operand" "rm,0")
16371           (match_operand:SWI248 3 "nonimmediate_operand" "0,rm")))]
16372   "TARGET_CMOVE && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16373   "@
16374    cmov%O2%C1\t{%2, %0|%0, %2}
16375    cmov%O2%c1\t{%3, %0|%0, %3}"
16376   [(set_attr "type" "icmov")
16377    (set_attr "mode" "<MODE>")])
16378
16379 (define_insn "*movqicc_noc"
16380   [(set (match_operand:QI 0 "register_operand" "=r,r")
16381         (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
16382                            [(reg FLAGS_REG) (const_int 0)])
16383                       (match_operand:QI 2 "register_operand" "r,0")
16384                       (match_operand:QI 3 "register_operand" "0,r")))]
16385   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
16386   "#"
16387   [(set_attr "type" "icmov")
16388    (set_attr "mode" "QI")])
16389
16390 (define_split
16391   [(set (match_operand 0 "register_operand")
16392         (if_then_else (match_operator 1 "ix86_comparison_operator"
16393                         [(reg FLAGS_REG) (const_int 0)])
16394                       (match_operand 2 "register_operand")
16395                       (match_operand 3 "register_operand")))]
16396   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL
16397    && (GET_MODE (operands[0]) == QImode
16398        || GET_MODE (operands[0]) == HImode)
16399    && reload_completed"
16400   [(set (match_dup 0)
16401         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
16402 {
16403   operands[0] = gen_lowpart (SImode, operands[0]);
16404   operands[2] = gen_lowpart (SImode, operands[2]);
16405   operands[3] = gen_lowpart (SImode, operands[3]);
16406 })
16407
16408 (define_expand "mov<mode>cc"
16409   [(set (match_operand:X87MODEF 0 "register_operand" "")
16410         (if_then_else:X87MODEF
16411           (match_operand 1 "ix86_fp_comparison_operator" "")
16412           (match_operand:X87MODEF 2 "register_operand" "")
16413           (match_operand:X87MODEF 3 "register_operand" "")))]
16414   "(TARGET_80387 && TARGET_CMOVE)
16415    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
16416   "if (ix86_expand_fp_movcc (operands)) DONE; else FAIL;")
16417
16418 (define_insn "*movxfcc_1"
16419   [(set (match_operand:XF 0 "register_operand" "=f,f")
16420         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
16421                                 [(reg FLAGS_REG) (const_int 0)])
16422                       (match_operand:XF 2 "register_operand" "f,0")
16423                       (match_operand:XF 3 "register_operand" "0,f")))]
16424   "TARGET_80387 && TARGET_CMOVE"
16425   "@
16426    fcmov%F1\t{%2, %0|%0, %2}
16427    fcmov%f1\t{%3, %0|%0, %3}"
16428   [(set_attr "type" "fcmov")
16429    (set_attr "mode" "XF")])
16430
16431 (define_insn "*movdfcc_1_rex64"
16432   [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
16433         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16434                                 [(reg FLAGS_REG) (const_int 0)])
16435                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16436                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16437   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16438    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16439   "@
16440    fcmov%F1\t{%2, %0|%0, %2}
16441    fcmov%f1\t{%3, %0|%0, %3}
16442    cmov%O2%C1\t{%2, %0|%0, %2}
16443    cmov%O2%c1\t{%3, %0|%0, %3}"
16444   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16445    (set_attr "mode" "DF,DF,DI,DI")])
16446
16447 (define_insn "*movdfcc_1"
16448   [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
16449         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16450                                 [(reg FLAGS_REG) (const_int 0)])
16451                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16452                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16453   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16454    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16455   "@
16456    fcmov%F1\t{%2, %0|%0, %2}
16457    fcmov%f1\t{%3, %0|%0, %3}
16458    #
16459    #"
16460   [(set_attr "type" "fcmov,fcmov,multi,multi")
16461    (set_attr "mode" "DF,DF,DI,DI")])
16462
16463 (define_split
16464   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand")
16465         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16466                                 [(reg FLAGS_REG) (const_int 0)])
16467                       (match_operand:DF 2 "nonimmediate_operand")
16468                       (match_operand:DF 3 "nonimmediate_operand")))]
16469   "!TARGET_64BIT && reload_completed"
16470   [(set (match_dup 2)
16471         (if_then_else:SI (match_dup 1) (match_dup 4) (match_dup 5)))
16472    (set (match_dup 3)
16473         (if_then_else:SI (match_dup 1) (match_dup 6) (match_dup 7)))]
16474 {
16475   split_double_mode (DImode, &operands[2], 2, &operands[4], &operands[6]);
16476   split_double_mode (DImode, &operands[0], 1, &operands[2], &operands[3]);
16477 })
16478
16479 (define_insn "*movsfcc_1_387"
16480   [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
16481         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
16482                                 [(reg FLAGS_REG) (const_int 0)])
16483                       (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
16484                       (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
16485   "TARGET_80387 && TARGET_CMOVE
16486    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16487   "@
16488    fcmov%F1\t{%2, %0|%0, %2}
16489    fcmov%f1\t{%3, %0|%0, %3}
16490    cmov%O2%C1\t{%2, %0|%0, %2}
16491    cmov%O2%c1\t{%3, %0|%0, %3}"
16492   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16493    (set_attr "mode" "SF,SF,SI,SI")])
16494
16495 ;; All moves in XOP pcmov instructions are 128 bits and hence we restrict
16496 ;; the scalar versions to have only XMM registers as operands.
16497
16498 ;; XOP conditional move
16499 (define_insn "*xop_pcmov_<mode>"
16500   [(set (match_operand:MODEF 0 "register_operand" "=x")
16501         (if_then_else:MODEF
16502           (match_operand:MODEF 1 "register_operand" "x")
16503           (match_operand:MODEF 2 "register_operand" "x")
16504           (match_operand:MODEF 3 "register_operand" "x")))]
16505   "TARGET_XOP"
16506   "vpcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
16507   [(set_attr "type" "sse4arg")])
16508
16509 ;; These versions of the min/max patterns are intentionally ignorant of
16510 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
16511 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
16512 ;; are undefined in this condition, we're certain this is correct.
16513
16514 (define_insn "<code><mode>3"
16515   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16516         (smaxmin:MODEF
16517           (match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
16518           (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")))]
16519   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16520   "@
16521    <maxmin_float><ssemodesuffix>\t{%2, %0|%0, %2}
16522    v<maxmin_float><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16523   [(set_attr "isa" "noavx,avx")
16524    (set_attr "prefix" "orig,vex")
16525    (set_attr "type" "sseadd")
16526    (set_attr "mode" "<MODE>")])
16527
16528 ;; These versions of the min/max patterns implement exactly the operations
16529 ;;   min = (op1 < op2 ? op1 : op2)
16530 ;;   max = (!(op1 < op2) ? op1 : op2)
16531 ;; Their operands are not commutative, and thus they may be used in the
16532 ;; presence of -0.0 and NaN.
16533
16534 (define_insn "*ieee_smin<mode>3"
16535   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16536         (unspec:MODEF
16537           [(match_operand:MODEF 1 "register_operand" "0,x")
16538            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16539          UNSPEC_IEEE_MIN))]
16540   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16541   "@
16542    min<ssemodesuffix>\t{%2, %0|%0, %2}
16543    vmin<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16544   [(set_attr "isa" "noavx,avx")
16545    (set_attr "prefix" "orig,vex")
16546    (set_attr "type" "sseadd")
16547    (set_attr "mode" "<MODE>")])
16548
16549 (define_insn "*ieee_smax<mode>3"
16550   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16551         (unspec:MODEF
16552           [(match_operand:MODEF 1 "register_operand" "0,x")
16553            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16554          UNSPEC_IEEE_MAX))]
16555   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16556   "@
16557    max<ssemodesuffix>\t{%2, %0|%0, %2}
16558    vmax<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16559   [(set_attr "isa" "noavx,avx")
16560    (set_attr "prefix" "orig,vex")
16561    (set_attr "type" "sseadd")
16562    (set_attr "mode" "<MODE>")])
16563
16564 ;; Make two stack loads independent:
16565 ;;   fld aa              fld aa
16566 ;;   fld %st(0)     ->   fld bb
16567 ;;   fmul bb             fmul %st(1), %st
16568 ;;
16569 ;; Actually we only match the last two instructions for simplicity.
16570 (define_peephole2
16571   [(set (match_operand 0 "fp_register_operand" "")
16572         (match_operand 1 "fp_register_operand" ""))
16573    (set (match_dup 0)
16574         (match_operator 2 "binary_fp_operator"
16575            [(match_dup 0)
16576             (match_operand 3 "memory_operand" "")]))]
16577   "REGNO (operands[0]) != REGNO (operands[1])"
16578   [(set (match_dup 0) (match_dup 3))
16579    (set (match_dup 0) (match_dup 4))]
16580
16581   ;; The % modifier is not operational anymore in peephole2's, so we have to
16582   ;; swap the operands manually in the case of addition and multiplication.
16583 {
16584   rtx op0, op1;
16585
16586   if (COMMUTATIVE_ARITH_P (operands[2]))
16587     op0 = operands[0], op1 = operands[1];
16588   else
16589     op0 = operands[1], op1 = operands[0];
16590
16591   operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]),
16592                                 GET_MODE (operands[2]),
16593                                 op0, op1);
16594 })
16595
16596 ;; Conditional addition patterns
16597 (define_expand "add<mode>cc"
16598   [(match_operand:SWI 0 "register_operand" "")
16599    (match_operand 1 "ordered_comparison_operator" "")
16600    (match_operand:SWI 2 "register_operand" "")
16601    (match_operand:SWI 3 "const_int_operand" "")]
16602   ""
16603   "if (ix86_expand_int_addcc (operands)) DONE; else FAIL;")
16604 \f
16605 ;; Misc patterns (?)
16606
16607 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
16608 ;; Otherwise there will be nothing to keep
16609 ;;
16610 ;; [(set (reg ebp) (reg esp))]
16611 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
16612 ;;  (clobber (eflags)]
16613 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
16614 ;;
16615 ;; in proper program order.
16616
16617 (define_insn "pro_epilogue_adjust_stack_<mode>_add"
16618   [(set (match_operand:P 0 "register_operand" "=r,r")
16619         (plus:P (match_operand:P 1 "register_operand" "0,r")
16620                 (match_operand:P 2 "<nonmemory_operand>" "r<i>,l<i>")))
16621    (clobber (reg:CC FLAGS_REG))
16622    (clobber (mem:BLK (scratch)))]
16623   ""
16624 {
16625   switch (get_attr_type (insn))
16626     {
16627     case TYPE_IMOV:
16628       return "mov{<imodesuffix>}\t{%1, %0|%0, %1}";
16629
16630     case TYPE_ALU:
16631       gcc_assert (rtx_equal_p (operands[0], operands[1]));
16632       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
16633         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
16634
16635       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
16636
16637     default:
16638       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
16639       return "lea{<imodesuffix>}\t{%E2, %0|%0, %E2}";
16640     }
16641 }
16642   [(set (attr "type")
16643         (cond [(and (eq_attr "alternative" "0")
16644                     (not (match_test "TARGET_OPT_AGU")))
16645                  (const_string "alu")
16646                (match_operand:<MODE> 2 "const0_operand" "")
16647                  (const_string "imov")
16648               ]
16649               (const_string "lea")))
16650    (set (attr "length_immediate")
16651         (cond [(eq_attr "type" "imov")
16652                  (const_string "0")
16653                (and (eq_attr "type" "alu")
16654                     (match_operand 2 "const128_operand" ""))
16655                  (const_string "1")
16656               ]
16657               (const_string "*")))
16658    (set_attr "mode" "<MODE>")])
16659
16660 (define_insn "pro_epilogue_adjust_stack_<mode>_sub"
16661   [(set (match_operand:P 0 "register_operand" "=r")
16662         (minus:P (match_operand:P 1 "register_operand" "0")
16663                  (match_operand:P 2 "register_operand" "r")))
16664    (clobber (reg:CC FLAGS_REG))
16665    (clobber (mem:BLK (scratch)))]
16666   ""
16667   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
16668   [(set_attr "type" "alu")
16669    (set_attr "mode" "<MODE>")])
16670
16671 (define_insn "allocate_stack_worker_probe_<mode>"
16672   [(set (match_operand:P 0 "register_operand" "=a")
16673         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16674                             UNSPECV_STACK_PROBE))
16675    (clobber (reg:CC FLAGS_REG))]
16676   "ix86_target_stack_probe ()"
16677   "call\t___chkstk_ms"
16678   [(set_attr "type" "multi")
16679    (set_attr "length" "5")])
16680
16681 (define_expand "allocate_stack"
16682   [(match_operand 0 "register_operand" "")
16683    (match_operand 1 "general_operand" "")]
16684   "ix86_target_stack_probe ()"
16685 {
16686   rtx x;
16687
16688 #ifndef CHECK_STACK_LIMIT
16689 #define CHECK_STACK_LIMIT 0
16690 #endif
16691
16692   if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
16693       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
16694     {
16695       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
16696                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16697       if (x != stack_pointer_rtx)
16698         emit_move_insn (stack_pointer_rtx, x);
16699     }
16700   else
16701     {
16702       x = copy_to_mode_reg (Pmode, operands[1]);
16703       if (TARGET_64BIT)
16704         emit_insn (gen_allocate_stack_worker_probe_di (x, x));
16705       else
16706         emit_insn (gen_allocate_stack_worker_probe_si (x, x));
16707       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, x,
16708                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16709       if (x != stack_pointer_rtx)
16710         emit_move_insn (stack_pointer_rtx, x);
16711     }
16712
16713   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
16714   DONE;
16715 })
16716
16717 ;; Use IOR for stack probes, this is shorter.
16718 (define_expand "probe_stack"
16719   [(match_operand 0 "memory_operand" "")]
16720   ""
16721 {
16722   rtx (*gen_ior3) (rtx, rtx, rtx);
16723
16724   gen_ior3 = (GET_MODE (operands[0]) == DImode
16725               ? gen_iordi3 : gen_iorsi3);
16726
16727   emit_insn (gen_ior3 (operands[0], operands[0], const0_rtx));
16728   DONE;
16729 })
16730
16731 (define_insn "adjust_stack_and_probe<mode>"
16732   [(set (match_operand:P 0 "register_operand" "=r")
16733         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16734                             UNSPECV_PROBE_STACK_RANGE))
16735    (set (reg:P SP_REG)
16736         (minus:P (reg:P SP_REG) (match_operand:P 2 "const_int_operand" "n")))
16737    (clobber (reg:CC FLAGS_REG))
16738    (clobber (mem:BLK (scratch)))]
16739   ""
16740   "* return output_adjust_stack_and_probe (operands[0]);"
16741   [(set_attr "type" "multi")])
16742
16743 (define_insn "probe_stack_range<mode>"
16744   [(set (match_operand:P 0 "register_operand" "=r")
16745         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")
16746                             (match_operand:P 2 "const_int_operand" "n")]
16747                             UNSPECV_PROBE_STACK_RANGE))
16748    (clobber (reg:CC FLAGS_REG))]
16749   ""
16750   "* return output_probe_stack_range (operands[0], operands[2]);"
16751   [(set_attr "type" "multi")])
16752
16753 (define_expand "builtin_setjmp_receiver"
16754   [(label_ref (match_operand 0 "" ""))]
16755   "!TARGET_64BIT && flag_pic"
16756 {
16757 #if TARGET_MACHO
16758   if (TARGET_MACHO)
16759     {
16760       rtx xops[3];
16761       rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
16762       rtx label_rtx = gen_label_rtx ();
16763       emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
16764       xops[0] = xops[1] = picreg;
16765       xops[2] = machopic_gen_offset (gen_rtx_LABEL_REF (SImode, label_rtx));
16766       ix86_expand_binary_operator (MINUS, SImode, xops);
16767     }
16768   else
16769 #endif
16770     emit_insn (gen_set_got (pic_offset_table_rtx));
16771   DONE;
16772 })
16773 \f
16774 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
16775
16776 (define_split
16777   [(set (match_operand 0 "register_operand" "")
16778         (match_operator 3 "promotable_binary_operator"
16779            [(match_operand 1 "register_operand" "")
16780             (match_operand 2 "aligned_operand" "")]))
16781    (clobber (reg:CC FLAGS_REG))]
16782   "! TARGET_PARTIAL_REG_STALL && reload_completed
16783    && ((GET_MODE (operands[0]) == HImode
16784         && ((optimize_function_for_speed_p (cfun) && !TARGET_FAST_PREFIX)
16785             /* ??? next two lines just !satisfies_constraint_K (...) */
16786             || !CONST_INT_P (operands[2])
16787             || satisfies_constraint_K (operands[2])))
16788        || (GET_MODE (operands[0]) == QImode
16789            && (TARGET_PROMOTE_QImode || optimize_function_for_size_p (cfun))))"
16790   [(parallel [(set (match_dup 0)
16791                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
16792               (clobber (reg:CC FLAGS_REG))])]
16793 {
16794   operands[0] = gen_lowpart (SImode, operands[0]);
16795   operands[1] = gen_lowpart (SImode, operands[1]);
16796   if (GET_CODE (operands[3]) != ASHIFT)
16797     operands[2] = gen_lowpart (SImode, operands[2]);
16798   PUT_MODE (operands[3], SImode);
16799 })
16800
16801 ; Promote the QImode tests, as i386 has encoding of the AND
16802 ; instruction with 32-bit sign-extended immediate and thus the
16803 ; instruction size is unchanged, except in the %eax case for
16804 ; which it is increased by one byte, hence the ! optimize_size.
16805 (define_split
16806   [(set (match_operand 0 "flags_reg_operand" "")
16807         (match_operator 2 "compare_operator"
16808           [(and (match_operand 3 "aligned_operand" "")
16809                 (match_operand 4 "const_int_operand" ""))
16810            (const_int 0)]))
16811    (set (match_operand 1 "register_operand" "")
16812         (and (match_dup 3) (match_dup 4)))]
16813   "! TARGET_PARTIAL_REG_STALL && reload_completed
16814    && optimize_insn_for_speed_p ()
16815    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
16816        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
16817    /* Ensure that the operand will remain sign-extended immediate.  */
16818    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
16819   [(parallel [(set (match_dup 0)
16820                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
16821                                     (const_int 0)]))
16822               (set (match_dup 1)
16823                    (and:SI (match_dup 3) (match_dup 4)))])]
16824 {
16825   operands[4]
16826     = gen_int_mode (INTVAL (operands[4])
16827                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
16828   operands[1] = gen_lowpart (SImode, operands[1]);
16829   operands[3] = gen_lowpart (SImode, operands[3]);
16830 })
16831
16832 ; Don't promote the QImode tests, as i386 doesn't have encoding of
16833 ; the TEST instruction with 32-bit sign-extended immediate and thus
16834 ; the instruction size would at least double, which is not what we
16835 ; want even with ! optimize_size.
16836 (define_split
16837   [(set (match_operand 0 "flags_reg_operand" "")
16838         (match_operator 1 "compare_operator"
16839           [(and (match_operand:HI 2 "aligned_operand" "")
16840                 (match_operand:HI 3 "const_int_operand" ""))
16841            (const_int 0)]))]
16842   "! TARGET_PARTIAL_REG_STALL && reload_completed
16843    && ! TARGET_FAST_PREFIX
16844    && optimize_insn_for_speed_p ()
16845    /* Ensure that the operand will remain sign-extended immediate.  */
16846    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
16847   [(set (match_dup 0)
16848         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
16849                          (const_int 0)]))]
16850 {
16851   operands[3]
16852     = gen_int_mode (INTVAL (operands[3])
16853                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
16854   operands[2] = gen_lowpart (SImode, operands[2]);
16855 })
16856
16857 (define_split
16858   [(set (match_operand 0 "register_operand" "")
16859         (neg (match_operand 1 "register_operand" "")))
16860    (clobber (reg:CC FLAGS_REG))]
16861   "! TARGET_PARTIAL_REG_STALL && reload_completed
16862    && (GET_MODE (operands[0]) == HImode
16863        || (GET_MODE (operands[0]) == QImode
16864            && (TARGET_PROMOTE_QImode
16865                || optimize_insn_for_size_p ())))"
16866   [(parallel [(set (match_dup 0)
16867                    (neg:SI (match_dup 1)))
16868               (clobber (reg:CC FLAGS_REG))])]
16869 {
16870   operands[0] = gen_lowpart (SImode, operands[0]);
16871   operands[1] = gen_lowpart (SImode, operands[1]);
16872 })
16873
16874 (define_split
16875   [(set (match_operand 0 "register_operand" "")
16876         (not (match_operand 1 "register_operand" "")))]
16877   "! TARGET_PARTIAL_REG_STALL && reload_completed
16878    && (GET_MODE (operands[0]) == HImode
16879        || (GET_MODE (operands[0]) == QImode
16880            && (TARGET_PROMOTE_QImode
16881                || optimize_insn_for_size_p ())))"
16882   [(set (match_dup 0)
16883         (not:SI (match_dup 1)))]
16884 {
16885   operands[0] = gen_lowpart (SImode, operands[0]);
16886   operands[1] = gen_lowpart (SImode, operands[1]);
16887 })
16888 \f
16889 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
16890 ;; transform a complex memory operation into two memory to register operations.
16891
16892 ;; Don't push memory operands
16893 (define_peephole2
16894   [(set (match_operand:SWI 0 "push_operand" "")
16895         (match_operand:SWI 1 "memory_operand" ""))
16896    (match_scratch:SWI 2 "<r>")]
16897   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16898    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16899   [(set (match_dup 2) (match_dup 1))
16900    (set (match_dup 0) (match_dup 2))])
16901
16902 ;; We need to handle SFmode only, because DFmode and XFmode are split to
16903 ;; SImode pushes.
16904 (define_peephole2
16905   [(set (match_operand:SF 0 "push_operand" "")
16906         (match_operand:SF 1 "memory_operand" ""))
16907    (match_scratch:SF 2 "r")]
16908   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16909    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16910   [(set (match_dup 2) (match_dup 1))
16911    (set (match_dup 0) (match_dup 2))])
16912
16913 ;; Don't move an immediate directly to memory when the instruction
16914 ;; gets too big.
16915 (define_peephole2
16916   [(match_scratch:SWI124 1 "<r>")
16917    (set (match_operand:SWI124 0 "memory_operand" "")
16918         (const_int 0))]
16919   "optimize_insn_for_speed_p ()
16920    && !TARGET_USE_MOV0
16921    && TARGET_SPLIT_LONG_MOVES
16922    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
16923    && peep2_regno_dead_p (0, FLAGS_REG)"
16924   [(parallel [(set (match_dup 2) (const_int 0))
16925               (clobber (reg:CC FLAGS_REG))])
16926    (set (match_dup 0) (match_dup 1))]
16927   "operands[2] = gen_lowpart (SImode, operands[1]);")
16928
16929 (define_peephole2
16930   [(match_scratch:SWI124 2 "<r>")
16931    (set (match_operand:SWI124 0 "memory_operand" "")
16932         (match_operand:SWI124 1 "immediate_operand" ""))]
16933   "optimize_insn_for_speed_p ()
16934    && TARGET_SPLIT_LONG_MOVES
16935    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
16936   [(set (match_dup 2) (match_dup 1))
16937    (set (match_dup 0) (match_dup 2))])
16938
16939 ;; Don't compare memory with zero, load and use a test instead.
16940 (define_peephole2
16941   [(set (match_operand 0 "flags_reg_operand" "")
16942         (match_operator 1 "compare_operator"
16943           [(match_operand:SI 2 "memory_operand" "")
16944            (const_int 0)]))
16945    (match_scratch:SI 3 "r")]
16946   "optimize_insn_for_speed_p () && ix86_match_ccmode (insn, CCNOmode)"
16947   [(set (match_dup 3) (match_dup 2))
16948    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))])
16949
16950 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
16951 ;; Don't split NOTs with a displacement operand, because resulting XOR
16952 ;; will not be pairable anyway.
16953 ;;
16954 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
16955 ;; represented using a modRM byte.  The XOR replacement is long decoded,
16956 ;; so this split helps here as well.
16957 ;;
16958 ;; Note: Can't do this as a regular split because we can't get proper
16959 ;; lifetime information then.
16960
16961 (define_peephole2
16962   [(set (match_operand:SWI124 0 "nonimmediate_operand" "")
16963         (not:SWI124 (match_operand:SWI124 1 "nonimmediate_operand" "")))]
16964   "optimize_insn_for_speed_p ()
16965    && ((TARGET_NOT_UNPAIRABLE
16966         && (!MEM_P (operands[0])
16967             || !memory_displacement_operand (operands[0], <MODE>mode)))
16968        || (TARGET_NOT_VECTORMODE
16969            && long_memory_operand (operands[0], <MODE>mode)))
16970    && peep2_regno_dead_p (0, FLAGS_REG)"
16971   [(parallel [(set (match_dup 0)
16972                    (xor:SWI124 (match_dup 1) (const_int -1)))
16973               (clobber (reg:CC FLAGS_REG))])])
16974
16975 ;; Non pairable "test imm, reg" instructions can be translated to
16976 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
16977 ;; byte opcode instead of two, have a short form for byte operands),
16978 ;; so do it for other CPUs as well.  Given that the value was dead,
16979 ;; this should not create any new dependencies.  Pass on the sub-word
16980 ;; versions if we're concerned about partial register stalls.
16981
16982 (define_peephole2
16983   [(set (match_operand 0 "flags_reg_operand" "")
16984         (match_operator 1 "compare_operator"
16985           [(and:SI (match_operand:SI 2 "register_operand" "")
16986                    (match_operand:SI 3 "immediate_operand" ""))
16987            (const_int 0)]))]
16988   "ix86_match_ccmode (insn, CCNOmode)
16989    && (true_regnum (operands[2]) != AX_REG
16990        || satisfies_constraint_K (operands[3]))
16991    && peep2_reg_dead_p (1, operands[2])"
16992   [(parallel
16993      [(set (match_dup 0)
16994            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
16995                             (const_int 0)]))
16996       (set (match_dup 2)
16997            (and:SI (match_dup 2) (match_dup 3)))])])
16998
16999 ;; We don't need to handle HImode case, because it will be promoted to SImode
17000 ;; on ! TARGET_PARTIAL_REG_STALL
17001
17002 (define_peephole2
17003   [(set (match_operand 0 "flags_reg_operand" "")
17004         (match_operator 1 "compare_operator"
17005           [(and:QI (match_operand:QI 2 "register_operand" "")
17006                    (match_operand:QI 3 "immediate_operand" ""))
17007            (const_int 0)]))]
17008   "! TARGET_PARTIAL_REG_STALL
17009    && ix86_match_ccmode (insn, CCNOmode)
17010    && true_regnum (operands[2]) != AX_REG
17011    && peep2_reg_dead_p (1, operands[2])"
17012   [(parallel
17013      [(set (match_dup 0)
17014            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
17015                             (const_int 0)]))
17016       (set (match_dup 2)
17017            (and:QI (match_dup 2) (match_dup 3)))])])
17018
17019 (define_peephole2
17020   [(set (match_operand 0 "flags_reg_operand" "")
17021         (match_operator 1 "compare_operator"
17022           [(and:SI
17023              (zero_extract:SI
17024                (match_operand 2 "ext_register_operand" "")
17025                (const_int 8)
17026                (const_int 8))
17027              (match_operand 3 "const_int_operand" ""))
17028            (const_int 0)]))]
17029   "! TARGET_PARTIAL_REG_STALL
17030    && ix86_match_ccmode (insn, CCNOmode)
17031    && true_regnum (operands[2]) != AX_REG
17032    && peep2_reg_dead_p (1, operands[2])"
17033   [(parallel [(set (match_dup 0)
17034                    (match_op_dup 1
17035                      [(and:SI
17036                         (zero_extract:SI
17037                           (match_dup 2)
17038                           (const_int 8)
17039                           (const_int 8))
17040                         (match_dup 3))
17041                       (const_int 0)]))
17042               (set (zero_extract:SI (match_dup 2)
17043                                     (const_int 8)
17044                                     (const_int 8))
17045                    (and:SI
17046                      (zero_extract:SI
17047                        (match_dup 2)
17048                        (const_int 8)
17049                        (const_int 8))
17050                      (match_dup 3)))])])
17051
17052 ;; Don't do logical operations with memory inputs.
17053 (define_peephole2
17054   [(match_scratch:SI 2 "r")
17055    (parallel [(set (match_operand:SI 0 "register_operand" "")
17056                    (match_operator:SI 3 "arith_or_logical_operator"
17057                      [(match_dup 0)
17058                       (match_operand:SI 1 "memory_operand" "")]))
17059               (clobber (reg:CC FLAGS_REG))])]
17060   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17061   [(set (match_dup 2) (match_dup 1))
17062    (parallel [(set (match_dup 0)
17063                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
17064               (clobber (reg:CC FLAGS_REG))])])
17065
17066 (define_peephole2
17067   [(match_scratch:SI 2 "r")
17068    (parallel [(set (match_operand:SI 0 "register_operand" "")
17069                    (match_operator:SI 3 "arith_or_logical_operator"
17070                      [(match_operand:SI 1 "memory_operand" "")
17071                       (match_dup 0)]))
17072               (clobber (reg:CC FLAGS_REG))])]
17073   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17074   [(set (match_dup 2) (match_dup 1))
17075    (parallel [(set (match_dup 0)
17076                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
17077               (clobber (reg:CC FLAGS_REG))])])
17078
17079 ;; Prefer Load+RegOp to Mov+MemOp.  Watch out for cases when the memory address
17080 ;; refers to the destination of the load!
17081
17082 (define_peephole2
17083   [(set (match_operand:SI 0 "register_operand" "")
17084         (match_operand:SI 1 "register_operand" ""))
17085    (parallel [(set (match_dup 0)
17086                    (match_operator:SI 3 "commutative_operator"
17087                      [(match_dup 0)
17088                       (match_operand:SI 2 "memory_operand" "")]))
17089               (clobber (reg:CC FLAGS_REG))])]
17090   "REGNO (operands[0]) != REGNO (operands[1])
17091    && GENERAL_REGNO_P (REGNO (operands[0]))
17092    && GENERAL_REGNO_P (REGNO (operands[1]))"
17093   [(set (match_dup 0) (match_dup 4))
17094    (parallel [(set (match_dup 0)
17095                    (match_op_dup 3 [(match_dup 0) (match_dup 1)]))
17096               (clobber (reg:CC FLAGS_REG))])]
17097   "operands[4] = replace_rtx (operands[2], operands[0], operands[1]);")
17098
17099 (define_peephole2
17100   [(set (match_operand 0 "register_operand" "")
17101         (match_operand 1 "register_operand" ""))
17102    (set (match_dup 0)
17103                    (match_operator 3 "commutative_operator"
17104                      [(match_dup 0)
17105                       (match_operand 2 "memory_operand" "")]))]
17106   "REGNO (operands[0]) != REGNO (operands[1])
17107    && ((MMX_REG_P (operands[0]) && MMX_REG_P (operands[1])) 
17108        || (SSE_REG_P (operands[0]) && SSE_REG_P (operands[1])))"
17109   [(set (match_dup 0) (match_dup 2))
17110    (set (match_dup 0)
17111         (match_op_dup 3 [(match_dup 0) (match_dup 1)]))])
17112
17113 ; Don't do logical operations with memory outputs
17114 ;
17115 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
17116 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
17117 ; the same decoder scheduling characteristics as the original.
17118
17119 (define_peephole2
17120   [(match_scratch:SI 2 "r")
17121    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17122                    (match_operator:SI 3 "arith_or_logical_operator"
17123                      [(match_dup 0)
17124                       (match_operand:SI 1 "nonmemory_operand" "")]))
17125               (clobber (reg:CC FLAGS_REG))])]
17126   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17127    /* Do not split stack checking probes.  */
17128    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17129   [(set (match_dup 2) (match_dup 0))
17130    (parallel [(set (match_dup 2)
17131                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
17132               (clobber (reg:CC FLAGS_REG))])
17133    (set (match_dup 0) (match_dup 2))])
17134
17135 (define_peephole2
17136   [(match_scratch:SI 2 "r")
17137    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17138                    (match_operator:SI 3 "arith_or_logical_operator"
17139                      [(match_operand:SI 1 "nonmemory_operand" "")
17140                       (match_dup 0)]))
17141               (clobber (reg:CC FLAGS_REG))])]
17142   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17143    /* Do not split stack checking probes.  */
17144    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17145   [(set (match_dup 2) (match_dup 0))
17146    (parallel [(set (match_dup 2)
17147                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
17148               (clobber (reg:CC FLAGS_REG))])
17149    (set (match_dup 0) (match_dup 2))])
17150
17151 ;; Attempt to use arith or logical operations with memory outputs with
17152 ;; setting of flags.
17153 (define_peephole2
17154   [(set (match_operand:SWI 0 "register_operand" "")
17155         (match_operand:SWI 1 "memory_operand" ""))
17156    (parallel [(set (match_dup 0)
17157                    (match_operator:SWI 3 "plusminuslogic_operator"
17158                      [(match_dup 0)
17159                       (match_operand:SWI 2 "<nonmemory_operand>" "")]))
17160               (clobber (reg:CC FLAGS_REG))])
17161    (set (match_dup 1) (match_dup 0))
17162    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17163   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17164    && peep2_reg_dead_p (4, operands[0])
17165    && !reg_overlap_mentioned_p (operands[0], operands[1])
17166    && (<MODE>mode != QImode
17167        || immediate_operand (operands[2], QImode)
17168        || q_regs_operand (operands[2], QImode))
17169    && ix86_match_ccmode (peep2_next_insn (3),
17170                          (GET_CODE (operands[3]) == PLUS
17171                           || GET_CODE (operands[3]) == MINUS)
17172                          ? CCGOCmode : CCNOmode)"
17173   [(parallel [(set (match_dup 4) (match_dup 5))
17174               (set (match_dup 1) (match_op_dup 3 [(match_dup 1)
17175                                                   (match_dup 2)]))])]
17176 {
17177   operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17178   operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17179                                 copy_rtx (operands[1]),
17180                                 copy_rtx (operands[2]));
17181   operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17182                                  operands[5], const0_rtx);
17183 })
17184
17185 (define_peephole2
17186   [(parallel [(set (match_operand:SWI 0 "register_operand" "")
17187                    (match_operator:SWI 2 "plusminuslogic_operator"
17188                      [(match_dup 0)
17189                       (match_operand:SWI 1 "memory_operand" "")]))
17190               (clobber (reg:CC FLAGS_REG))])
17191    (set (match_dup 1) (match_dup 0))
17192    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17193   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17194    && GET_CODE (operands[2]) != MINUS
17195    && peep2_reg_dead_p (3, operands[0])
17196    && !reg_overlap_mentioned_p (operands[0], operands[1])
17197    && ix86_match_ccmode (peep2_next_insn (2),
17198                          GET_CODE (operands[2]) == PLUS
17199                          ? CCGOCmode : CCNOmode)"
17200   [(parallel [(set (match_dup 3) (match_dup 4))
17201               (set (match_dup 1) (match_op_dup 2 [(match_dup 1)
17202                                                   (match_dup 0)]))])]
17203 {
17204   operands[3] = SET_DEST (PATTERN (peep2_next_insn (2)));
17205   operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), <MODE>mode,
17206                                 copy_rtx (operands[1]),
17207                                 copy_rtx (operands[0]));
17208   operands[4] = gen_rtx_COMPARE (GET_MODE (operands[3]),
17209                                  operands[4], const0_rtx);
17210 })
17211
17212 (define_peephole2
17213   [(set (match_operand:SWI12 0 "register_operand" "")
17214         (match_operand:SWI12 1 "memory_operand" ""))
17215    (parallel [(set (match_operand:SI 4 "register_operand" "")
17216                    (match_operator:SI 3 "plusminuslogic_operator"
17217                      [(match_dup 4)
17218                       (match_operand:SI 2 "nonmemory_operand" "")]))
17219               (clobber (reg:CC FLAGS_REG))])
17220    (set (match_dup 1) (match_dup 0))
17221    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17222   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17223    && REG_P (operands[0]) && REG_P (operands[4])
17224    && REGNO (operands[0]) == REGNO (operands[4])
17225    && peep2_reg_dead_p (4, operands[0])
17226    && (<MODE>mode != QImode
17227        || immediate_operand (operands[2], SImode)
17228        || q_regs_operand (operands[2], SImode))
17229    && !reg_overlap_mentioned_p (operands[0], operands[1])
17230    && ix86_match_ccmode (peep2_next_insn (3),
17231                          (GET_CODE (operands[3]) == PLUS
17232                           || GET_CODE (operands[3]) == MINUS)
17233                          ? CCGOCmode : CCNOmode)"
17234   [(parallel [(set (match_dup 4) (match_dup 5))
17235               (set (match_dup 1) (match_dup 6))])]
17236 {
17237   operands[2] = gen_lowpart (<MODE>mode, operands[2]);
17238   operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17239   operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17240                                 copy_rtx (operands[1]), operands[2]);
17241   operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17242                                  operands[5], const0_rtx);
17243   operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17244                                 copy_rtx (operands[1]),
17245                                 copy_rtx (operands[2]));
17246 })
17247
17248 ;; Attempt to always use XOR for zeroing registers.
17249 (define_peephole2
17250   [(set (match_operand 0 "register_operand" "")
17251         (match_operand 1 "const0_operand" ""))]
17252   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
17253    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17254    && GENERAL_REG_P (operands[0])
17255    && peep2_regno_dead_p (0, FLAGS_REG)"
17256   [(parallel [(set (match_dup 0) (const_int 0))
17257               (clobber (reg:CC FLAGS_REG))])]
17258   "operands[0] = gen_lowpart (word_mode, operands[0]);")
17259
17260 (define_peephole2
17261   [(set (strict_low_part (match_operand 0 "register_operand" ""))
17262         (const_int 0))]
17263   "(GET_MODE (operands[0]) == QImode
17264     || GET_MODE (operands[0]) == HImode)
17265    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17266    && peep2_regno_dead_p (0, FLAGS_REG)"
17267   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
17268               (clobber (reg:CC FLAGS_REG))])])
17269
17270 ;; For HI, SI and DI modes, or $-1,reg is smaller than mov $-1,reg.
17271 (define_peephole2
17272   [(set (match_operand:SWI248 0 "register_operand" "")
17273         (const_int -1))]
17274   "(optimize_insn_for_size_p () || TARGET_MOVE_M1_VIA_OR)
17275    && peep2_regno_dead_p (0, FLAGS_REG)"
17276   [(parallel [(set (match_dup 0) (const_int -1))
17277               (clobber (reg:CC FLAGS_REG))])]
17278 {
17279   if (GET_MODE_SIZE (<MODE>mode) < GET_MODE_SIZE (SImode))
17280     operands[0] = gen_lowpart (SImode, operands[0]);
17281 })
17282
17283 ;; Attempt to convert simple lea to add/shift.
17284 ;; These can be created by move expanders.
17285
17286 (define_peephole2
17287   [(set (match_operand:SWI48 0 "register_operand" "")
17288         (plus:SWI48 (match_dup 0)
17289                     (match_operand:SWI48 1 "<nonmemory_operand>" "")))]
17290   "peep2_regno_dead_p (0, FLAGS_REG)"
17291   [(parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (match_dup 1)))
17292               (clobber (reg:CC FLAGS_REG))])])
17293
17294 (define_peephole2
17295   [(set (match_operand:SI 0 "register_operand" "")
17296         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
17297                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
17298   "TARGET_64BIT
17299    && peep2_regno_dead_p (0, FLAGS_REG)
17300    && REGNO (operands[0]) == REGNO (operands[1])"
17301   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
17302               (clobber (reg:CC FLAGS_REG))])]
17303   "operands[2] = gen_lowpart (SImode, operands[2]);")
17304
17305 (define_peephole2
17306   [(set (match_operand:SWI48 0 "register_operand" "")
17307         (mult:SWI48 (match_dup 0)
17308                     (match_operand:SWI48 1 "const_int_operand" "")))]
17309   "exact_log2 (INTVAL (operands[1])) >= 0
17310    && peep2_regno_dead_p (0, FLAGS_REG)"
17311   [(parallel [(set (match_dup 0) (ashift:SWI48 (match_dup 0) (match_dup 2)))
17312               (clobber (reg:CC FLAGS_REG))])]
17313   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
17314
17315 (define_peephole2
17316   [(set (match_operand:SI 0 "register_operand" "")
17317         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
17318                    (match_operand:DI 2 "const_int_operand" "")) 0))]
17319   "TARGET_64BIT
17320    && exact_log2 (INTVAL (operands[2])) >= 0
17321    && REGNO (operands[0]) == REGNO (operands[1])
17322    && peep2_regno_dead_p (0, FLAGS_REG)"
17323   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
17324               (clobber (reg:CC FLAGS_REG))])]
17325   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
17326
17327 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
17328 ;; code is shorter, since push is only 1 byte, while add imm, %esp is 3 bytes.
17329 ;; On many CPUs it is also faster, since special hardware to avoid esp
17330 ;; dependencies is present.
17331
17332 ;; While some of these conversions may be done using splitters, we use
17333 ;; peepholes in order to allow combine_stack_adjustments pass to see
17334 ;; nonobfuscated RTL.
17335
17336 ;; Convert prologue esp subtractions to push.
17337 ;; We need register to push.  In order to keep verify_flow_info happy we have
17338 ;; two choices
17339 ;; - use scratch and clobber it in order to avoid dependencies
17340 ;; - use already live register
17341 ;; We can't use the second way right now, since there is no reliable way how to
17342 ;; verify that given register is live.  First choice will also most likely in
17343 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
17344 ;; call clobbered registers are dead.  We may want to use base pointer as an
17345 ;; alternative when no register is available later.
17346
17347 (define_peephole2
17348   [(match_scratch:P 1 "r")
17349    (parallel [(set (reg:P SP_REG)
17350                    (plus:P (reg:P SP_REG)
17351                            (match_operand:P 0 "const_int_operand" "")))
17352               (clobber (reg:CC FLAGS_REG))
17353               (clobber (mem:BLK (scratch)))])]
17354   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17355    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17356   [(clobber (match_dup 1))
17357    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17358               (clobber (mem:BLK (scratch)))])])
17359
17360 (define_peephole2
17361   [(match_scratch:P 1 "r")
17362    (parallel [(set (reg:P SP_REG)
17363                    (plus:P (reg:P SP_REG)
17364                            (match_operand:P 0 "const_int_operand" "")))
17365               (clobber (reg:CC FLAGS_REG))
17366               (clobber (mem:BLK (scratch)))])]
17367   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17368    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17369   [(clobber (match_dup 1))
17370    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17371    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17372               (clobber (mem:BLK (scratch)))])])
17373
17374 ;; Convert esp subtractions to push.
17375 (define_peephole2
17376   [(match_scratch:P 1 "r")
17377    (parallel [(set (reg:P SP_REG)
17378                    (plus:P (reg:P SP_REG)
17379                            (match_operand:P 0 "const_int_operand" "")))
17380               (clobber (reg:CC FLAGS_REG))])]
17381   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17382    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17383   [(clobber (match_dup 1))
17384    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17385
17386 (define_peephole2
17387   [(match_scratch:P 1 "r")
17388    (parallel [(set (reg:P SP_REG)
17389                    (plus:P (reg:P SP_REG)
17390                            (match_operand:P 0 "const_int_operand" "")))
17391               (clobber (reg:CC FLAGS_REG))])]
17392   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17393    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17394   [(clobber (match_dup 1))
17395    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17396    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17397
17398 ;; Convert epilogue deallocator to pop.
17399 (define_peephole2
17400   [(match_scratch:P 1 "r")
17401    (parallel [(set (reg:P SP_REG)
17402                    (plus:P (reg:P SP_REG)
17403                            (match_operand:P 0 "const_int_operand" "")))
17404               (clobber (reg:CC FLAGS_REG))
17405               (clobber (mem:BLK (scratch)))])]
17406   "(TARGET_SINGLE_POP || optimize_insn_for_size_p ())
17407    && INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17408   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17409               (clobber (mem:BLK (scratch)))])])
17410
17411 ;; Two pops case is tricky, since pop causes dependency
17412 ;; on destination register.  We use two registers if available.
17413 (define_peephole2
17414   [(match_scratch:P 1 "r")
17415    (match_scratch:P 2 "r")
17416    (parallel [(set (reg:P SP_REG)
17417                    (plus:P (reg:P SP_REG)
17418                            (match_operand:P 0 "const_int_operand" "")))
17419               (clobber (reg:CC FLAGS_REG))
17420               (clobber (mem:BLK (scratch)))])]
17421   "(TARGET_DOUBLE_POP || optimize_insn_for_size_p ())
17422    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17423   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17424               (clobber (mem:BLK (scratch)))])
17425    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17426
17427 (define_peephole2
17428   [(match_scratch:P 1 "r")
17429    (parallel [(set (reg:P SP_REG)
17430                    (plus:P (reg:P SP_REG)
17431                            (match_operand:P 0 "const_int_operand" "")))
17432               (clobber (reg:CC FLAGS_REG))
17433               (clobber (mem:BLK (scratch)))])]
17434   "optimize_insn_for_size_p ()
17435    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17436   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17437               (clobber (mem:BLK (scratch)))])
17438    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17439
17440 ;; Convert esp additions to pop.
17441 (define_peephole2
17442   [(match_scratch:P 1 "r")
17443    (parallel [(set (reg:P SP_REG)
17444                    (plus:P (reg:P SP_REG)
17445                            (match_operand:P 0 "const_int_operand" "")))
17446               (clobber (reg:CC FLAGS_REG))])]
17447   "INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17448   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17449
17450 ;; Two pops case is tricky, since pop causes dependency
17451 ;; on destination register.  We use two registers if available.
17452 (define_peephole2
17453   [(match_scratch:P 1 "r")
17454    (match_scratch:P 2 "r")
17455    (parallel [(set (reg:P SP_REG)
17456                    (plus:P (reg:P SP_REG)
17457                            (match_operand:P 0 "const_int_operand" "")))
17458               (clobber (reg:CC FLAGS_REG))])]
17459   "INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17460   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17461    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17462
17463 (define_peephole2
17464   [(match_scratch:P 1 "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   "optimize_insn_for_size_p ()
17470    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17471   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17472    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17473 \f
17474 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
17475 ;; required and register dies.  Similarly for 128 to -128.
17476 (define_peephole2
17477   [(set (match_operand 0 "flags_reg_operand" "")
17478         (match_operator 1 "compare_operator"
17479           [(match_operand 2 "register_operand" "")
17480            (match_operand 3 "const_int_operand" "")]))]
17481   "(((!TARGET_FUSE_CMP_AND_BRANCH || optimize_insn_for_size_p ())
17482      && incdec_operand (operands[3], GET_MODE (operands[3])))
17483     || (!TARGET_FUSE_CMP_AND_BRANCH
17484         && INTVAL (operands[3]) == 128))
17485    && ix86_match_ccmode (insn, CCGCmode)
17486    && peep2_reg_dead_p (1, operands[2])"
17487   [(parallel [(set (match_dup 0)
17488                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
17489               (clobber (match_dup 2))])])
17490 \f
17491 ;; Convert imul by three, five and nine into lea
17492 (define_peephole2
17493   [(parallel
17494     [(set (match_operand:SWI48 0 "register_operand" "")
17495           (mult:SWI48 (match_operand:SWI48 1 "register_operand" "")
17496                       (match_operand:SWI48 2 "const359_operand" "")))
17497      (clobber (reg:CC FLAGS_REG))])]
17498   "!TARGET_PARTIAL_REG_STALL
17499    || <MODE>mode == SImode
17500    || optimize_function_for_size_p (cfun)"
17501   [(set (match_dup 0)
17502         (plus:SWI48 (mult:SWI48 (match_dup 1) (match_dup 2))
17503                     (match_dup 1)))]
17504   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17505
17506 (define_peephole2
17507   [(parallel
17508     [(set (match_operand:SWI48 0 "register_operand" "")
17509           (mult:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
17510                       (match_operand:SWI48 2 "const359_operand" "")))
17511      (clobber (reg:CC FLAGS_REG))])]
17512   "optimize_insn_for_speed_p ()
17513    && (!TARGET_PARTIAL_REG_STALL || <MODE>mode == SImode)"
17514   [(set (match_dup 0) (match_dup 1))
17515    (set (match_dup 0)
17516         (plus:SWI48 (mult:SWI48 (match_dup 0) (match_dup 2))
17517                     (match_dup 0)))]
17518   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17519
17520 ;; imul $32bit_imm, mem, reg is vector decoded, while
17521 ;; imul $32bit_imm, reg, reg is direct decoded.
17522 (define_peephole2
17523   [(match_scratch:SWI48 3 "r")
17524    (parallel [(set (match_operand:SWI48 0 "register_operand" "")
17525                    (mult:SWI48 (match_operand:SWI48 1 "memory_operand" "")
17526                                (match_operand:SWI48 2 "immediate_operand" "")))
17527               (clobber (reg:CC FLAGS_REG))])]
17528   "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17529    && !satisfies_constraint_K (operands[2])"
17530   [(set (match_dup 3) (match_dup 1))
17531    (parallel [(set (match_dup 0) (mult:SWI48 (match_dup 3) (match_dup 2)))
17532               (clobber (reg:CC FLAGS_REG))])])
17533
17534 (define_peephole2
17535   [(match_scratch:SI 3 "r")
17536    (parallel [(set (match_operand:DI 0 "register_operand" "")
17537                    (zero_extend:DI
17538                      (mult:SI (match_operand:SI 1 "memory_operand" "")
17539                               (match_operand:SI 2 "immediate_operand" ""))))
17540               (clobber (reg:CC FLAGS_REG))])]
17541   "TARGET_64BIT
17542    && TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17543    && !satisfies_constraint_K (operands[2])"
17544   [(set (match_dup 3) (match_dup 1))
17545    (parallel [(set (match_dup 0)
17546                    (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
17547               (clobber (reg:CC FLAGS_REG))])])
17548
17549 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
17550 ;; Convert it into imul reg, reg
17551 ;; It would be better to force assembler to encode instruction using long
17552 ;; immediate, but there is apparently no way to do so.
17553 (define_peephole2
17554   [(parallel [(set (match_operand:SWI248 0 "register_operand" "")
17555                    (mult:SWI248
17556                     (match_operand:SWI248 1 "nonimmediate_operand" "")
17557                     (match_operand:SWI248 2 "const_int_operand" "")))
17558               (clobber (reg:CC FLAGS_REG))])
17559    (match_scratch:SWI248 3 "r")]
17560   "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()
17561    && satisfies_constraint_K (operands[2])"
17562   [(set (match_dup 3) (match_dup 2))
17563    (parallel [(set (match_dup 0) (mult:SWI248 (match_dup 0) (match_dup 3)))
17564               (clobber (reg:CC FLAGS_REG))])]
17565 {
17566   if (!rtx_equal_p (operands[0], operands[1]))
17567     emit_move_insn (operands[0], operands[1]);
17568 })
17569
17570 ;; After splitting up read-modify operations, array accesses with memory
17571 ;; operands might end up in form:
17572 ;;  sall    $2, %eax
17573 ;;  movl    4(%esp), %edx
17574 ;;  addl    %edx, %eax
17575 ;; instead of pre-splitting:
17576 ;;  sall    $2, %eax
17577 ;;  addl    4(%esp), %eax
17578 ;; Turn it into:
17579 ;;  movl    4(%esp), %edx
17580 ;;  leal    (%edx,%eax,4), %eax
17581
17582 (define_peephole2
17583   [(match_scratch:P 5 "r")
17584    (parallel [(set (match_operand 0 "register_operand" "")
17585                    (ashift (match_operand 1 "register_operand" "")
17586                            (match_operand 2 "const_int_operand" "")))
17587                (clobber (reg:CC FLAGS_REG))])
17588    (parallel [(set (match_operand 3 "register_operand" "")
17589                    (plus (match_dup 0)
17590                          (match_operand 4 "x86_64_general_operand" "")))
17591                    (clobber (reg:CC FLAGS_REG))])]
17592   "IN_RANGE (INTVAL (operands[2]), 1, 3)
17593    /* Validate MODE for lea.  */
17594    && ((!TARGET_PARTIAL_REG_STALL
17595         && (GET_MODE (operands[0]) == QImode
17596             || GET_MODE (operands[0]) == HImode))
17597        || GET_MODE (operands[0]) == SImode
17598        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
17599    && (rtx_equal_p (operands[0], operands[3])
17600        || peep2_reg_dead_p (2, operands[0]))
17601    /* We reorder load and the shift.  */
17602    && !reg_overlap_mentioned_p (operands[0], operands[4])"
17603   [(set (match_dup 5) (match_dup 4))
17604    (set (match_dup 0) (match_dup 1))]
17605 {
17606   enum machine_mode op1mode = GET_MODE (operands[1]);
17607   enum machine_mode mode = op1mode == DImode ? DImode : SImode;
17608   int scale = 1 << INTVAL (operands[2]);
17609   rtx index = gen_lowpart (Pmode, operands[1]);
17610   rtx base = gen_lowpart (Pmode, operands[5]);
17611   rtx dest = gen_lowpart (mode, operands[3]);
17612
17613   operands[1] = gen_rtx_PLUS (Pmode, base,
17614                               gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
17615   operands[5] = base;
17616   if (mode != Pmode)
17617     operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
17618   if (op1mode != Pmode)
17619     operands[5] = gen_rtx_SUBREG (op1mode, operands[5], 0);
17620   operands[0] = dest;
17621 })
17622 \f
17623 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
17624 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
17625 ;; caught for use by garbage collectors and the like.  Using an insn that
17626 ;; maps to SIGILL makes it more likely the program will rightfully die.
17627 ;; Keeping with tradition, "6" is in honor of #UD.
17628 (define_insn "trap"
17629   [(trap_if (const_int 1) (const_int 6))]
17630   ""
17631   { return ASM_SHORT "0x0b0f"; }
17632   [(set_attr "length" "2")])
17633
17634 (define_expand "prefetch"
17635   [(prefetch (match_operand 0 "address_operand" "")
17636              (match_operand:SI 1 "const_int_operand" "")
17637              (match_operand:SI 2 "const_int_operand" ""))]
17638   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
17639 {
17640   int rw = INTVAL (operands[1]);
17641   int locality = INTVAL (operands[2]);
17642
17643   gcc_assert (rw == 0 || rw == 1);
17644   gcc_assert (IN_RANGE (locality, 0, 3));
17645
17646   if (TARGET_PREFETCHW && rw)
17647     operands[2] = GEN_INT (3);
17648   /* Use 3dNOW prefetch in case we are asking for write prefetch not
17649      supported by SSE counterpart or the SSE prefetch is not available
17650      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
17651      of locality.  */
17652   else if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
17653     operands[2] = GEN_INT (3);
17654   else
17655     operands[1] = const0_rtx;
17656 })
17657
17658 (define_insn "*prefetch_sse"
17659   [(prefetch (match_operand 0 "address_operand" "p")
17660              (const_int 0)
17661              (match_operand:SI 1 "const_int_operand" ""))]
17662   "TARGET_PREFETCH_SSE"
17663 {
17664   static const char * const patterns[4] = {
17665    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
17666   };
17667
17668   int locality = INTVAL (operands[1]);
17669   gcc_assert (IN_RANGE (locality, 0, 3));
17670
17671   return patterns[locality];
17672 }
17673   [(set_attr "type" "sse")
17674    (set_attr "atom_sse_attr" "prefetch")
17675    (set (attr "length_address")
17676         (symbol_ref "memory_address_length (operands[0], false)"))
17677    (set_attr "memory" "none")])
17678
17679 (define_insn "*prefetch_3dnow"
17680   [(prefetch (match_operand 0 "address_operand" "p")
17681              (match_operand:SI 1 "const_int_operand" "n")
17682              (const_int 3))]
17683   "TARGET_3DNOW || TARGET_PREFETCHW"
17684 {
17685   if (INTVAL (operands[1]) == 0)
17686     return "prefetch\t%a0";
17687   else
17688     return "prefetchw\t%a0";
17689 }
17690   [(set_attr "type" "mmx")
17691    (set (attr "length_address")
17692         (symbol_ref "memory_address_length (operands[0], false)"))
17693    (set_attr "memory" "none")])
17694
17695 (define_expand "stack_protect_set"
17696   [(match_operand 0 "memory_operand" "")
17697    (match_operand 1 "memory_operand" "")]
17698   "!TARGET_HAS_BIONIC"
17699 {
17700   rtx (*insn)(rtx, rtx);
17701
17702 #ifdef TARGET_THREAD_SSP_OFFSET
17703   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17704   insn = (TARGET_LP64
17705           ? gen_stack_tls_protect_set_di
17706           : gen_stack_tls_protect_set_si);
17707 #else
17708   insn = (TARGET_LP64
17709           ? gen_stack_protect_set_di
17710           : gen_stack_protect_set_si);
17711 #endif
17712
17713   emit_insn (insn (operands[0], operands[1]));
17714   DONE;
17715 })
17716
17717 (define_insn "stack_protect_set_<mode>"
17718   [(set (match_operand:PTR 0 "memory_operand" "=m")
17719         (unspec:PTR [(match_operand:PTR 1 "memory_operand" "m")]
17720                     UNSPEC_SP_SET))
17721    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17722    (clobber (reg:CC FLAGS_REG))]
17723   "!TARGET_HAS_BIONIC"
17724   "mov{<imodesuffix>}\t{%1, %2|%2, %1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17725   [(set_attr "type" "multi")])
17726
17727 (define_insn "stack_tls_protect_set_<mode>"
17728   [(set (match_operand:PTR 0 "memory_operand" "=m")
17729         (unspec:PTR [(match_operand:PTR 1 "const_int_operand" "i")]
17730                     UNSPEC_SP_TLS_SET))
17731    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17732    (clobber (reg:CC FLAGS_REG))]
17733   ""
17734   "mov{<imodesuffix>}\t{%@:%P1, %2|%2, <iptrsize> PTR %@:%P1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17735   [(set_attr "type" "multi")])
17736
17737 (define_expand "stack_protect_test"
17738   [(match_operand 0 "memory_operand" "")
17739    (match_operand 1 "memory_operand" "")
17740    (match_operand 2 "" "")]
17741   "!TARGET_HAS_BIONIC"
17742 {
17743   rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
17744
17745   rtx (*insn)(rtx, rtx, rtx);
17746
17747 #ifdef TARGET_THREAD_SSP_OFFSET
17748   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17749   insn = (TARGET_LP64
17750           ? gen_stack_tls_protect_test_di
17751           : gen_stack_tls_protect_test_si);
17752 #else
17753   insn = (TARGET_LP64
17754           ? gen_stack_protect_test_di
17755           : gen_stack_protect_test_si);
17756 #endif
17757
17758   emit_insn (insn (flags, operands[0], operands[1]));
17759
17760   emit_jump_insn (gen_cbranchcc4 (gen_rtx_EQ (VOIDmode, flags, const0_rtx),
17761                                   flags, const0_rtx, operands[2]));
17762   DONE;
17763 })
17764
17765 (define_insn "stack_protect_test_<mode>"
17766   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
17767         (unspec:CCZ [(match_operand:PTR 1 "memory_operand" "m")
17768                      (match_operand:PTR 2 "memory_operand" "m")]
17769                     UNSPEC_SP_TEST))
17770    (clobber (match_scratch:PTR 3 "=&r"))]
17771   "!TARGET_HAS_BIONIC"
17772   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%2, %3|%3, %2}"
17773   [(set_attr "type" "multi")])
17774
17775 (define_insn "stack_tls_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 "const_int_operand" "i")]
17779                     UNSPEC_SP_TLS_TEST))
17780    (clobber (match_scratch:PTR 3 "=r"))]
17781   ""
17782   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%@:%P2, %3|%3, <iptrsize> PTR %@:%P2}"
17783   [(set_attr "type" "multi")])
17784
17785 (define_insn "sse4_2_crc32<mode>"
17786   [(set (match_operand:SI 0 "register_operand" "=r")
17787         (unspec:SI
17788           [(match_operand:SI 1 "register_operand" "0")
17789            (match_operand:SWI124 2 "nonimmediate_operand" "<r>m")]
17790           UNSPEC_CRC32))]
17791   "TARGET_SSE4_2 || TARGET_CRC32"
17792   "crc32{<imodesuffix>}\t{%2, %0|%0, %2}"
17793   [(set_attr "type" "sselog1")
17794    (set_attr "prefix_rep" "1")
17795    (set_attr "prefix_extra" "1")
17796    (set (attr "prefix_data16")
17797      (if_then_else (match_operand:HI 2 "" "")
17798        (const_string "1")
17799        (const_string "*")))
17800    (set (attr "prefix_rex")
17801      (if_then_else (match_operand:QI 2 "ext_QIreg_operand" "")
17802        (const_string "1")
17803        (const_string "*")))
17804    (set_attr "mode" "SI")])
17805
17806 (define_insn "sse4_2_crc32di"
17807   [(set (match_operand:DI 0 "register_operand" "=r")
17808         (unspec:DI
17809           [(match_operand:DI 1 "register_operand" "0")
17810            (match_operand:DI 2 "nonimmediate_operand" "rm")]
17811           UNSPEC_CRC32))]
17812   "TARGET_64BIT && (TARGET_SSE4_2 || TARGET_CRC32)"
17813   "crc32{q}\t{%2, %0|%0, %2}"
17814   [(set_attr "type" "sselog1")
17815    (set_attr "prefix_rep" "1")
17816    (set_attr "prefix_extra" "1")
17817    (set_attr "mode" "DI")])
17818
17819 (define_expand "rdpmc"
17820   [(match_operand:DI 0 "register_operand" "")
17821    (match_operand:SI 1 "register_operand" "")]
17822   ""
17823 {
17824   rtx reg = gen_reg_rtx (DImode);
17825   rtx si;
17826
17827   /* Force operand 1 into ECX.  */
17828   rtx ecx = gen_rtx_REG (SImode, CX_REG);
17829   emit_insn (gen_rtx_SET (VOIDmode, ecx, operands[1]));
17830   si = gen_rtx_UNSPEC_VOLATILE (DImode, gen_rtvec (1, ecx),
17831                                 UNSPECV_RDPMC);
17832
17833   if (TARGET_64BIT)
17834     {
17835       rtvec vec = rtvec_alloc (2);
17836       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17837       rtx upper = gen_reg_rtx (DImode);
17838       rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17839                                         gen_rtvec (1, const0_rtx),
17840                                         UNSPECV_RDPMC);
17841       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, si);
17842       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17843       emit_insn (load);
17844       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17845                                    NULL, 1, OPTAB_DIRECT);
17846       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17847                                  OPTAB_DIRECT);
17848     }
17849   else
17850     emit_insn (gen_rtx_SET (VOIDmode, reg, si));
17851   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17852   DONE;
17853 })
17854
17855 (define_insn "*rdpmc"
17856   [(set (match_operand:DI 0 "register_operand" "=A")
17857         (unspec_volatile:DI [(match_operand:SI 1 "register_operand" "c")]
17858                             UNSPECV_RDPMC))]
17859   "!TARGET_64BIT"
17860   "rdpmc"
17861   [(set_attr "type" "other")
17862    (set_attr "length" "2")])
17863
17864 (define_insn "*rdpmc_rex64"
17865   [(set (match_operand:DI 0 "register_operand" "=a")
17866         (unspec_volatile:DI [(match_operand:SI 2 "register_operand" "c")]
17867                             UNSPECV_RDPMC))
17868   (set (match_operand:DI 1 "register_operand" "=d")
17869        (unspec_volatile:DI [(const_int 0)] UNSPECV_RDPMC))]
17870   "TARGET_64BIT"
17871   "rdpmc"
17872   [(set_attr "type" "other")
17873    (set_attr "length" "2")])
17874
17875 (define_expand "rdtsc"
17876   [(set (match_operand:DI 0 "register_operand" "")
17877         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17878   ""
17879 {
17880   if (TARGET_64BIT)
17881     {
17882       rtvec vec = rtvec_alloc (2);
17883       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17884       rtx upper = gen_reg_rtx (DImode);
17885       rtx lower = gen_reg_rtx (DImode);
17886       rtx src = gen_rtx_UNSPEC_VOLATILE (DImode,
17887                                          gen_rtvec (1, const0_rtx),
17888                                          UNSPECV_RDTSC);
17889       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, lower, src);
17890       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, src);
17891       emit_insn (load);
17892       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17893                                    NULL, 1, OPTAB_DIRECT);
17894       lower = expand_simple_binop (DImode, IOR, lower, upper, lower, 1,
17895                                    OPTAB_DIRECT);
17896       emit_insn (gen_rtx_SET (VOIDmode, operands[0], lower));
17897       DONE;
17898     }
17899 })
17900
17901 (define_insn "*rdtsc"
17902   [(set (match_operand:DI 0 "register_operand" "=A")
17903         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17904   "!TARGET_64BIT"
17905   "rdtsc"
17906   [(set_attr "type" "other")
17907    (set_attr "length" "2")])
17908
17909 (define_insn "*rdtsc_rex64"
17910   [(set (match_operand:DI 0 "register_operand" "=a")
17911         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))
17912    (set (match_operand:DI 1 "register_operand" "=d")
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_expand "rdtscp"
17920   [(match_operand:DI 0 "register_operand" "")
17921    (match_operand:SI 1 "memory_operand" "")]
17922   ""
17923 {
17924   rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17925                                     gen_rtvec (1, const0_rtx),
17926                                     UNSPECV_RDTSCP);
17927   rtx si = gen_rtx_UNSPEC_VOLATILE (SImode,
17928                                     gen_rtvec (1, const0_rtx),
17929                                     UNSPECV_RDTSCP);
17930   rtx reg = gen_reg_rtx (DImode);
17931   rtx tmp = gen_reg_rtx (SImode);
17932
17933   if (TARGET_64BIT)
17934     {
17935       rtvec vec = rtvec_alloc (3);
17936       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17937       rtx upper = gen_reg_rtx (DImode);
17938       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17939       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17940       RTVEC_ELT (vec, 2) = gen_rtx_SET (VOIDmode, tmp, si);
17941       emit_insn (load);
17942       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17943                                    NULL, 1, OPTAB_DIRECT);
17944       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17945                                  OPTAB_DIRECT);
17946     }
17947   else
17948     {
17949       rtvec vec = rtvec_alloc (2);
17950       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17951       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17952       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, tmp, si);
17953       emit_insn (load);
17954     }
17955   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17956   emit_insn (gen_rtx_SET (VOIDmode, operands[1], tmp));
17957   DONE;
17958 })
17959
17960 (define_insn "*rdtscp"
17961   [(set (match_operand:DI 0 "register_operand" "=A")
17962         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17963    (set (match_operand:SI 1 "register_operand" "=c")
17964         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
17965   "!TARGET_64BIT"
17966   "rdtscp"
17967   [(set_attr "type" "other")
17968    (set_attr "length" "3")])
17969
17970 (define_insn "*rdtscp_rex64"
17971   [(set (match_operand:DI 0 "register_operand" "=a")
17972         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17973    (set (match_operand:DI 1 "register_operand" "=d")
17974         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17975    (set (match_operand:SI 2 "register_operand" "=c")
17976         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
17977   "TARGET_64BIT"
17978   "rdtscp"
17979   [(set_attr "type" "other")
17980    (set_attr "length" "3")])
17981
17982 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
17983 ;;
17984 ;; LWP instructions
17985 ;;
17986 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
17987
17988 (define_expand "lwp_llwpcb"
17989   [(unspec_volatile [(match_operand 0 "register_operand" "r")]
17990                     UNSPECV_LLWP_INTRINSIC)]
17991   "TARGET_LWP")
17992
17993 (define_insn "*lwp_llwpcb<mode>1"
17994   [(unspec_volatile [(match_operand:P 0 "register_operand" "r")]
17995                     UNSPECV_LLWP_INTRINSIC)]
17996   "TARGET_LWP"
17997   "llwpcb\t%0"
17998   [(set_attr "type" "lwp")
17999    (set_attr "mode" "<MODE>")
18000    (set_attr "length" "5")])
18001
18002 (define_expand "lwp_slwpcb"
18003   [(set (match_operand 0 "register_operand" "=r")
18004         (unspec_volatile [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18005   "TARGET_LWP"
18006 {
18007   rtx (*insn)(rtx);
18008
18009   insn = (TARGET_64BIT
18010           ? gen_lwp_slwpcbdi
18011           : gen_lwp_slwpcbsi);
18012
18013   emit_insn (insn (operands[0]));
18014   DONE;
18015 })
18016
18017 (define_insn "lwp_slwpcb<mode>"
18018   [(set (match_operand:P 0 "register_operand" "=r")
18019         (unspec_volatile:P [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18020   "TARGET_LWP"
18021   "slwpcb\t%0"
18022   [(set_attr "type" "lwp")
18023    (set_attr "mode" "<MODE>")
18024    (set_attr "length" "5")])
18025
18026 (define_expand "lwp_lwpval<mode>3"
18027   [(unspec_volatile [(match_operand:SWI48 1 "register_operand" "r")
18028                      (match_operand:SI 2 "nonimmediate_operand" "rm")
18029                      (match_operand:SI 3 "const_int_operand" "i")]
18030                     UNSPECV_LWPVAL_INTRINSIC)]
18031   "TARGET_LWP"
18032   ;; Avoid unused variable warning.
18033   "(void) operands[0];")
18034
18035 (define_insn "*lwp_lwpval<mode>3_1"
18036   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")
18037                      (match_operand:SI 1 "nonimmediate_operand" "rm")
18038                      (match_operand:SI 2 "const_int_operand" "i")]
18039                     UNSPECV_LWPVAL_INTRINSIC)]
18040   "TARGET_LWP"
18041   "lwpval\t{%2, %1, %0|%0, %1, %2}"
18042   [(set_attr "type" "lwp")
18043    (set_attr "mode" "<MODE>")
18044    (set (attr "length")
18045         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18046
18047 (define_expand "lwp_lwpins<mode>3"
18048   [(set (reg:CCC FLAGS_REG)
18049         (unspec_volatile:CCC [(match_operand:SWI48 1 "register_operand" "r")
18050                               (match_operand:SI 2 "nonimmediate_operand" "rm")
18051                               (match_operand:SI 3 "const_int_operand" "i")]
18052                              UNSPECV_LWPINS_INTRINSIC))
18053    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
18054         (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))]
18055   "TARGET_LWP")
18056
18057 (define_insn "*lwp_lwpins<mode>3_1"
18058   [(set (reg:CCC FLAGS_REG)
18059         (unspec_volatile:CCC [(match_operand:SWI48 0 "register_operand" "r")
18060                               (match_operand:SI 1 "nonimmediate_operand" "rm")
18061                               (match_operand:SI 2 "const_int_operand" "i")]
18062                              UNSPECV_LWPINS_INTRINSIC))]
18063   "TARGET_LWP"
18064   "lwpins\t{%2, %1, %0|%0, %1, %2}"
18065   [(set_attr "type" "lwp")
18066    (set_attr "mode" "<MODE>")
18067    (set (attr "length")
18068         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18069
18070 (define_insn "rdfsbase<mode>"
18071   [(set (match_operand:SWI48 0 "register_operand" "=r")
18072         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDFSBASE))]
18073   "TARGET_64BIT && TARGET_FSGSBASE"
18074   "rdfsbase %0"
18075   [(set_attr "type" "other")
18076    (set_attr "prefix_extra" "2")])
18077
18078 (define_insn "rdgsbase<mode>"
18079   [(set (match_operand:SWI48 0 "register_operand" "=r")
18080         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDGSBASE))]
18081   "TARGET_64BIT && TARGET_FSGSBASE"
18082   "rdgsbase %0"
18083   [(set_attr "type" "other")
18084    (set_attr "prefix_extra" "2")])
18085
18086 (define_insn "wrfsbase<mode>"
18087   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18088                     UNSPECV_WRFSBASE)]
18089   "TARGET_64BIT && TARGET_FSGSBASE"
18090   "wrfsbase %0"
18091   [(set_attr "type" "other")
18092    (set_attr "prefix_extra" "2")])
18093
18094 (define_insn "wrgsbase<mode>"
18095   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18096                     UNSPECV_WRGSBASE)]
18097   "TARGET_64BIT && TARGET_FSGSBASE"
18098   "wrgsbase %0"
18099   [(set_attr "type" "other")
18100    (set_attr "prefix_extra" "2")])
18101
18102 (define_insn "rdrand<mode>_1"
18103   [(set (match_operand:SWI248 0 "register_operand" "=r")
18104         (unspec_volatile:SWI248 [(const_int 0)] UNSPECV_RDRAND))
18105    (set (reg:CCC FLAGS_REG)
18106         (unspec_volatile:CCC [(const_int 0)] UNSPECV_RDRAND))]
18107   "TARGET_RDRND"
18108   "rdrand\t%0"
18109   [(set_attr "type" "other")
18110    (set_attr "prefix_extra" "1")])
18111
18112 (define_expand "pause"
18113   [(set (match_dup 0)
18114         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18115   ""
18116 {
18117   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
18118   MEM_VOLATILE_P (operands[0]) = 1;
18119 })
18120
18121 ;; Use "rep; nop", instead of "pause", to support older assemblers.
18122 ;; They have the same encoding.
18123 (define_insn "*pause"
18124   [(set (match_operand:BLK 0 "" "")
18125         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18126   ""
18127   "rep; nop"
18128   [(set_attr "length" "2")
18129    (set_attr "memory" "unknown")])
18130
18131 (include "mmx.md")
18132 (include "sse.md")
18133 (include "sync.md")